Skip to content

Commit 591a513

Browse files
committed
feat: add support for linking external flux apps
1 parent eaf5bf4 commit 591a513

33 files changed

+569
-345
lines changed

src/components/app/details/appDetails/IssuesCard.tsx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -82,16 +82,16 @@ const IssuesCard = ({ cardLoading, setErrorsList, toggleIssuesModal, setDetailed
8282
}, [appDetails])
8383

8484
useEffect(() => {
85-
if (appDetails.deploymentAppType === DeploymentAppTypes.GITOPS && appDetails.deploymentAppDeleteRequest) {
85+
if (appDetails.deploymentAppType === DeploymentAppTypes.ARGO && appDetails.deploymentAppDeleteRequest) {
8686
verifyDeployedClusterConnectionStatus()
8787
}
8888
}, [appDetails.appId, appDetails.environmentId])
8989

9090
const verifyDeployedClusterConnectionStatus = async (): Promise<void> => {
9191
await getClusterConnectionStatus(appDetails.environmentId).then((response: ClusterConnectionResponse) => {
9292
if (response.result) {
93-
response.result?.clusterReachable ? setClusterConnectionError(false) : setClusterConnectionError(true)
94-
setClusterName(response.result.clusterName)
93+
setClusterConnectionError(response.result.clusterReachable ?? false)
94+
setClusterName(response.result.clusterName ?? '')
9595
}
9696
})
9797
}

src/components/app/details/appDetails/SourceInfo.tsx

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,6 @@ export const SourceInfo = ({
9292
const [hibernationPatchResponseLoading, setHibernationPatchResponseLoading] = useState<boolean>(false)
9393

9494
const isdeploymentAppDeleting = appDetails?.deploymentAppDeleteRequest || false
95-
const isArgoCdApp = appDetails?.deploymentAppType === DeploymentAppTypes.GITOPS
9695
const status = appDetails?.resourceTree?.status || ''
9796
const conditions = appDetails?.resourceTree?.conditions
9897
let message = null

src/components/app/details/triggerView/workflow/nodes/triggerCDNode.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@ export class TriggerCDNode extends Component<TriggerCDNodeProps, TriggerCDNodeSt
4545
gitopsConflictLoading: false,
4646
reloadNoGitOpsRepoConfiguredModal: false,
4747
gitOpsRepoWarningCondition:
48-
this.props.deploymentAppType === DeploymentAppTypes.GITOPS && this.props.isGitOpsRepoNotConfigured,
48+
this.props.deploymentAppType === DeploymentAppTypes.ARGO && this.props.isGitOpsRepoNotConfigured,
4949
}
5050
}
5151

@@ -68,7 +68,7 @@ export class TriggerCDNode extends Component<TriggerCDNodeProps, TriggerCDNodeSt
6868
if (prevProps.isGitOpsRepoNotConfigured !== this.props.isGitOpsRepoNotConfigured) {
6969
this.setState({
7070
gitOpsRepoWarningCondition:
71-
this.props.deploymentAppType === DeploymentAppTypes.GITOPS && this.props.isGitOpsRepoNotConfigured,
71+
this.props.deploymentAppType === DeploymentAppTypes.ARGO && this.props.isGitOpsRepoNotConfigured,
7272
})
7373
}
7474
}

src/components/app/details/triggerView/workflow/nodes/triggerPrePostCDNode.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ import { getAppGroupDeploymentHistoryLink } from '../../../../../ApplicationGrou
3333

3434
export class TriggerPrePostCDNode extends Component<TriggerPrePostCDNodeProps, TriggerPrePostCDNodeState> {
3535
gitOpsRepoWarningCondition =
36-
this.props.deploymentAppType === DeploymentAppTypes.GITOPS && this.props.isGitOpsRepoNotConfigured
36+
this.props.deploymentAppType === DeploymentAppTypes.ARGO && this.props.isGitOpsRepoNotConfigured
3737

3838
constructor(props) {
3939
super(props)

src/components/app/list-new/AppListService.ts

Lines changed: 20 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -22,13 +22,15 @@ import {
2222
EnvironmentListHelmResult,
2323
Teams,
2424
getUrlWithSearchParams,
25+
APIOptions,
2526
} from '@devtron-labs/devtron-fe-common-lib'
2627
import moment from 'moment'
2728
import { Cluster } from '@Services/service.types'
2829
import { Moment12HourFormat, Routes } from '../../../config'
2930
import {
3031
AppListFilterConfig,
3132
AppListPayloadType,
33+
GenericAppListResponse,
3234
GenericAppType,
3335
GetDevtronHelmAppListParamsType,
3436
HelmAppListResponse,
@@ -49,18 +51,27 @@ export const getDevtronInstalledHelmApps = (
4951
return get(url)
5052
}
5153

52-
export const getArgoInstalledExternalApps = (clusterIdsCsv: string, abortControllerRef?: MutableRefObject<AbortController>): Promise<ResponseType<GenericAppType[]>> =>
53-
get(`${Routes.ARGO_APPS}${clusterIdsCsv ? `?clusterIds=${clusterIdsCsv}` : ''}`, { abortControllerRef })
54+
export const getArgoInstalledExternalApps = (
55+
clusterIdsCsv: string,
56+
abortControllerRef?: MutableRefObject<AbortController>,
57+
): Promise<ResponseType<GenericAppType[]>> => {
58+
const url = getUrlWithSearchParams(Routes.ARGO_APPS, { clusterIds: clusterIdsCsv })
59+
return get(url, { abortControllerRef })
60+
}
5461

5562
export const getDevtronAppListDataToExport = (
5663
filterConfig: AppListFilterConfig,
5764
environmentList: EnvListMinDTO[],
5865
namespaceList: EnvironmentListHelmResult[],
5966
clusterList: Cluster[],
6067
projectList: Teams[],
61-
appCount: number
68+
appCount: number,
6269
) => {
63-
const appListPayload: AppListPayloadType = {...getDevtronAppListPayload(filterConfig, environmentList, namespaceList), offset: 0, size: appCount} // Over riding size and offset as we need all list (no pagination)
70+
const appListPayload: AppListPayloadType = {
71+
...getDevtronAppListPayload(filterConfig, environmentList, namespaceList),
72+
offset: 0,
73+
size: appCount,
74+
} // Over riding size and offset as we need all list (no pagination)
6475
const clusterMap = new Map<string, number>()
6576
clusterList.forEach((cluster) => clusterMap.set(cluster.cluster_name, cluster.id))
6677
return getAppList(appListPayload).then(({ result }) => {
@@ -111,3 +122,8 @@ export const getDevtronAppListDataToExport = (
111122
return []
112123
})
113124
}
125+
126+
export const getFluxInstalledExternalApps = (clusterIdsCsv: string, options?: APIOptions) => {
127+
const url = getUrlWithSearchParams(Routes.FLUX_APPS, { clusterIds: clusterIdsCsv, noStream: true })
128+
return get<GenericAppListResponse>(url, options)
129+
}

src/components/cdPipeline/BuildCD.tsx

Lines changed: 2 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@ import { useContext, useState } from 'react'
1818
import {
1919
CustomInput,
2020
DeploymentAppTypes,
21-
InfoColourBar,
2221
Progressing,
2322
TippyCustomized,
2423
TippyTheme,
@@ -64,7 +63,7 @@ import { EnvironmentWithSelectPickerType } from '@Components/CIPipelineN/types'
6463
import { BuildCDProps } from './types'
6564
import { MigrateToDevtron } from './MigrateToDevtron'
6665
import TriggerTypeRadio from './TriggerTypeRadio'
67-
import { MigrateToDevtronProps } from './MigrateToDevtron/types'
66+
import { getDeploymentAppTypeLabel } from './MigrateToDevtron/utils'
6867

6968
const VirtualEnvSelectionInfoText = importComponentFromFELibrary('VirtualEnvSelectionInfoText')
7069
const HelmManifestPush = importComponentFromFELibrary('HelmManifestPush')
@@ -141,14 +140,6 @@ export default function BuildCD({
141140
setFormData(_form)
142141
}
143142

144-
const handleMigrateFromAppTypeChange: MigrateToDevtronProps['handleMigrateFromAppTypeChange'] = (event) => {
145-
const { value } = event.target as HTMLInputElement
146-
setMigrateToDevtronFormState((prevState) => ({
147-
...prevState,
148-
deploymentAppType: value as MigrateToDevtronFormState['deploymentAppType'],
149-
}))
150-
}
151-
152143
const handleNamespaceChange = (event): void => {
153144
const _form = { ...formData }
154145
_form.namespace = event.target.value
@@ -772,7 +763,6 @@ export default function BuildCD({
772763
<MigrateToDevtron
773764
migrateToDevtronFormState={migrateToDevtronFormState}
774765
setMigrateToDevtronFormState={setMigrateToDevtronFormState}
775-
handleMigrateFromAppTypeChange={handleMigrateFromAppTypeChange}
776766
/>
777767
)
778768
}
@@ -786,9 +776,7 @@ export default function BuildCD({
786776
<ICInfo className="dc__no-shrink icon-dim-20 dc__no-shrink" />
787777
<span className="fs-13 fw-4 lh-20 cn-9 dc__word-break">
788778
This deployment pipeline was linked to&nbsp;
789-
{formData.deploymentAppType === DeploymentAppTypes.GITOPS
790-
? 'Argo CD application'
791-
: 'helm release'}
779+
{getDeploymentAppTypeLabel(formData.deploymentAppType as DeploymentAppTypes)}
792780
&nbsp;: {formData.deploymentAppName}
793781
</span>
794782
</div>

src/components/cdPipeline/CDPipeline.tsx

Lines changed: 19 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,6 @@ import {
2525
VariableType,
2626
VisibleModal,
2727
PipelineType,
28-
ButtonWithLoader,
2928
MODAL_TYPE,
3029
ACTION_STATE,
3130
YAMLStringify,
@@ -54,11 +53,10 @@ import {
5453
ButtonStyleType,
5554
ButtonVariantType,
5655
ComponentSizeType,
56+
Icon,
5757
} from '@devtron-labs/devtron-fe-common-lib'
5858
import { useEffect, useMemo, useRef, useState } from 'react'
5959
import { Redirect, Route, Switch, useParams, useRouteMatch } from 'react-router-dom'
60-
import { ReactComponent as ICWarning } from '@Icons/ic-warning.svg'
61-
import { ReactComponent as Close } from '../../assets/icons/ic-close.svg'
6260
import { CDDeploymentTabText, RegistryPayloadType, SourceTypeMap, ViewType } from '../../config'
6361
import { getPluginIdsFromBuildStage, importComponentFromFELibrary, sortObjectArrayAlphabetically } from '../common'
6462
import BuildCD from './BuildCD'
@@ -111,6 +109,7 @@ import {
111109
import { BuildCDProps, CDPipelineProps, DeleteDialogType, ForceDeleteMessageType } from './types'
112110
import { MIGRATE_TO_DEVTRON_FORM_STATE } from './constants'
113111
import { getConfigureGitOpsCredentialsButtonProps } from '@Components/workflowEditor/ConfigureGitopsInfoBlock'
112+
import { getIsExternalAppLinkable } from './MigrateToDevtron/utils'
114113

115114
const DeploymentWindowConfirmationDialog = importComponentFromFELibrary('DeploymentWindowConfirmationDialog')
116115
const processPluginData: (params: ProcessPluginDataParamsType) => Promise<ProcessPluginDataReturnType> =
@@ -275,7 +274,7 @@ export default function CDPipeline({
275274

276275
const isExternalArgoPipeline =
277276
formData.releaseMode === ReleaseMode.MIGRATE_EXTERNAL_APPS &&
278-
formData.deploymentAppType === DeploymentAppTypes.GITOPS
277+
formData.deploymentAppType === DeploymentAppTypes.ARGO
279278

280279
const isGitOpsRepoNotConfigured = isExternalArgoPipeline ? false : isGitOpsRepoNotConfiguredProp
281280

@@ -942,7 +941,7 @@ export default function CDPipeline({
942941
setGitOpsRepoConfiguredWarning({ show: true, text: gitOpsRepoNotConfiguredWithOptionsHidden })
943942
}
944943
const isGitOpsRepoNotConfiguredAndOptionsVisible =
945-
formData.deploymentAppType === DeploymentAppTypes.GITOPS &&
944+
formData.deploymentAppType === DeploymentAppTypes.ARGO &&
946945
isGitOpsRepoNotConfigured &&
947946
!window._env_.HIDE_GITOPS_OR_HELM_OPTION
948947

@@ -973,7 +972,7 @@ export default function CDPipeline({
973972

974973
const savePipeline = async () => {
975974
if (!isMigratingFromExternalApp) {
976-
if (formData.deploymentAppType === DeploymentAppTypes.GITOPS && isGitOpsInstalledButNotConfigured) {
975+
if (formData.deploymentAppType === DeploymentAppTypes.ARGO && isGitOpsInstalledButNotConfigured) {
977976
ToastManager.showToast({
978977
variant: ToastVariantType.error,
979978
title: 'GitOps credentials not configured',
@@ -1092,7 +1091,7 @@ export default function CDPipeline({
10921091

10931092
const deleteCD = (force: boolean, cascadeDelete: boolean) => {
10941093
const isPartialDelete =
1095-
formData.deploymentAppType === DeploymentAppTypes.GITOPS && formData.deploymentAppCreated && !force
1094+
formData.deploymentAppType === DeploymentAppTypes.ARGO && formData.deploymentAppCreated && !force
10961095
const payload = {
10971096
action: isPartialDelete ? CD_PATCH_ACTION.DEPLOYMENT_PARTIAL_DELETE : CD_PATCH_ACTION.DELETE,
10981097
appId: parseInt(appId),
@@ -1220,7 +1219,7 @@ export default function CDPipeline({
12201219
>
12211220
Advanced options
12221221
{mandatoryPluginData && (!mandatoryPluginData.isValidPre || !mandatoryPluginData.isValidPost) && (
1223-
<ICWarning className="icon-dim-16 warning-icon-y7-imp dc__no-shrink" />
1222+
<Icon name='ic-warning' color='Y700' />
12241223
)}
12251224
</button>
12261225
)
@@ -1398,10 +1397,7 @@ export default function CDPipeline({
13981397
// Disable button if environment or release name is not selected
13991398
const getButtonDisabledMessage = (): string => {
14001399
if (isMigratingFromExternalApp) {
1401-
const isLinkable =
1402-
migrateToDevtronFormState.deploymentAppType === DeploymentAppTypes.HELM
1403-
? migrateToDevtronFormState.migrateFromHelmFormState.validationResponse.isLinkable
1404-
: migrateToDevtronFormState.migrateFromArgoFormState.validationResponse.isLinkable
1400+
const isLinkable = getIsExternalAppLinkable(migrateToDevtronFormState)
14051401
if (!isLinkable) {
14061402
return 'Please resolve errors before proceeding'
14071403
}
@@ -1427,12 +1423,19 @@ export default function CDPipeline({
14271423
}`}
14281424
>
14291425
<div className="flex flex-align-center flex-justify bg__primary px-20 py-12">
1430-
<h2 className="fs-16 fw-6 lh-1-43 m-0" data-testid="build-pipeline-heading">
1426+
<h2 className="fs-16 fw-6 lh-24 m-0" data-testid="build-pipeline-heading">
14311427
{title}
14321428
</h2>
1433-
<button type="button" className="dc__transparent flex icon-dim-24" onClick={closePipelineModal}>
1434-
<Close className="icon-dim-24" />
1435-
</button>
1429+
<Button
1430+
dataTestId="close-cd-modal"
1431+
icon={<Icon name="ic-close-large" color={null} />}
1432+
size={ComponentSizeType.small}
1433+
onClick={closePipelineModal}
1434+
ariaLabel="close modal"
1435+
showAriaLabelInTippy={false}
1436+
style={ButtonStyleType.negativeGrey}
1437+
variant={ButtonVariantType.borderLess}
1438+
/>
14361439
</div>
14371440

14381441
{!isAdvanced && !isTemplateView && (

src/components/cdPipeline/MigrateToDevtron/ClusterSelect.tsx

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@
1616

1717
import {
1818
ComponentSizeType,
19-
DeploymentAppTypes,
2019
ResourceKindType,
2120
SelectPicker,
2221
useGetResourceKindsOptions,
@@ -27,7 +26,7 @@ import { generateClusterOption } from './utils'
2726

2827
const RESOURCES_TO_FETCH: [ResourceKindType.cluster] = [ResourceKindType.cluster]
2928

30-
const ClusterSelect = ({ clusterId, clusterName, handleClusterChange, deploymentAppType }: ClusterSelectProps) => {
29+
const ClusterSelect = ({ clusterId, clusterName, handleClusterChange, label }: ClusterSelectProps) => {
3130
const { isResourcesOptionsLoading, refetchResourcesOptions, resourcesOptionsError, resourcesOptionsMap } =
3231
useGetResourceKindsOptions({
3332
resourcesToFetch: RESOURCES_TO_FETCH,
@@ -42,11 +41,7 @@ const ClusterSelect = ({ clusterId, clusterName, handleClusterChange, deployment
4241
<SelectPicker<SelectClusterOptionType['value'], false>
4342
inputId="migrate-from-source-cluster-select"
4443
classNamePrefix="migrate-from-source-cluster-select"
45-
label={
46-
deploymentAppType === DeploymentAppTypes.HELM
47-
? 'Cluster containing Helm Release'
48-
: 'Cluster containing Argo CD application'
49-
}
44+
label={label}
5045
isLoading={isResourcesOptionsLoading}
5146
optionListError={resourcesOptionsError}
5247
reloadOptionList={refetchResourcesOptions}

0 commit comments

Comments
 (0)