From b4788b6b4646a633122d7633f146d6bba7cc0d28 Mon Sep 17 00:00:00 2001 From: Surajyadav Date: Sun, 22 Dec 2024 20:35:32 +0530 Subject: [PATCH] sync-failed-option-added Signed-off-by: Surajyadav --- .../applications-list/applications-filter.tsx | 47 ++++++++++++------- 1 file changed, 30 insertions(+), 17 deletions(-) diff --git a/ui/src/app/applications/components/applications-list/applications-filter.tsx b/ui/src/app/applications/components/applications-list/applications-filter.tsx index 79534ee766d99..c018721b597de 100644 --- a/ui/src/app/applications/components/applications-list/applications-filter.tsx +++ b/ui/src/app/applications/components/applications-list/applications-filter.tsx @@ -7,6 +7,7 @@ import {AppsListPreferences, services} from '../../../shared/services'; import {Filter, FiltersGroup} from '../filter/filter'; import * as LabelSelector from '../label-selector'; import {ComparisonStatusIcon, getAppDefaultSource, HealthStatusIcon} from '../utils'; +import {COLORS} from '../../../shared/components'; export interface FilterResult { repos: boolean; @@ -35,7 +36,10 @@ export function getFilterResults(applications: Application[], pref: AppsListPref ...app, filterResult: { repos: pref.reposFilter.length === 0 || pref.reposFilter.includes(getAppDefaultSource(app).repoURL), - sync: pref.syncFilter.length === 0 || pref.syncFilter.includes(app.status.sync.status), + sync: + pref.syncFilter.length === 0 || + pref.syncFilter.includes(app.status.sync.status) || + (pref.syncFilter.includes('Sync failed') && app.status.operationState?.phase === 'Failed'), autosync: pref.autoSyncFilter.length === 0 || pref.autoSyncFilter.includes(getAutoSyncStatus(app.spec.syncPolicy)), health: pref.healthFilter.length === 0 || pref.healthFilter.includes(app.status.health.status), namespaces: pref.namespacesFilter.length === 0 || pref.namespacesFilter.some(ns => app.spec.destination.namespace && minimatch(app.spec.destination.namespace, ns)), @@ -96,22 +100,31 @@ const getOptions = (apps: FilteredApp[], filterType: keyof FilterResult, filter: }); }; -const SyncFilter = (props: AppFilterProps) => ( - props.onChange({...props.pref, syncFilter: s})} - options={getOptions( - props.apps, - 'sync', - app => app.status.sync.status, - Object.keys(SyncStatuses), - s => ( - - ) - )} - /> -); +const SyncFilter = (props: AppFilterProps) => { + const failedSyncOption = 'Sync failed'; + const options = [...Object.keys(SyncStatuses), failedSyncOption]; + + // counts for sync statuses + const counts = getCounts(props.apps, 'sync', app => app.status.sync.status, options); + + // counting failed operation phase separately + const failedCount = props.apps.filter( + app => app.status.operationState?.phase === 'Failed' && Object.keys(app.filterResult).every((key: keyof FilterResult) => key === 'sync' || app.filterResult[key]) + ).length; + + const filterOptions = options.map(status => ({ + label: status, + icon: + status === failedSyncOption ? ( + + ) : ( + + ), + count: status === failedSyncOption ? failedCount : counts.get(status) + })); + + return props.onChange({...props.pref, syncFilter: s})} options={filterOptions} />; +}; const HealthFilter = (props: AppFilterProps) => (