From a2bc69143fce11f75c106c319a3dfba7398c1133 Mon Sep 17 00:00:00 2001 From: Sergey Smolnikov Date: Mon, 9 Sep 2024 11:26:05 +0200 Subject: [PATCH] Fixed favorites --- Makefile | 3 + src/components/app-list-item/dev.tsx | 8 ++ src/components/app-list-item/index.tsx | 34 +++--- src/components/app-list/index.tsx | 100 +++++++++--------- src/components/app-list/style.css | 2 +- .../page-create-application/index.tsx | 2 +- src/effects/use-local-storage.ts | 9 +- src/style/objects.headings.css | 5 + 8 files changed, 97 insertions(+), 66 deletions(-) diff --git a/Makefile b/Makefile index 3499d88b8..5c8c3580d 100644 --- a/Makefile +++ b/Makefile @@ -31,6 +31,9 @@ lint: npm run "lint" npm run "lint-ts" +.PHONY: lint-fix +lint-fix: + npm run "lint-fix" .PHONY: lint-strict lint-strict: diff --git a/src/components/app-list-item/dev.tsx b/src/components/app-list-item/dev.tsx index cb53f22ad..99f920a86 100644 --- a/src/components/app-list-item/dev.tsx +++ b/src/components/app-list-item/dev.tsx @@ -13,6 +13,8 @@ const testData: Array<{ description: string } & AppListItemProps> = [ description: 'App', app: { name: 'test-app' }, handler: noop, + isLoaded: true, + name: 'some-app', }, { description: 'App, marked Favourite, with Job', @@ -29,6 +31,8 @@ const testData: Array<{ description: string } & AppListItemProps> = [ handler: noop, isFavourite: true, showStatus: true, + isLoaded: true, + name: 'some-app', }, { description: 'App, marked Favourite, without Job', @@ -36,12 +40,16 @@ const testData: Array<{ description: string } & AppListItemProps> = [ handler: noop, isFavourite: true, showStatus: true, + isLoaded: true, + name: 'some-app', }, { description: 'App, marked Placeholder', app: { name: 'app-placeholder' }, handler: noop, isPlaceholder: true, + isLoaded: true, + name: 'some-app', }, ]; diff --git a/src/components/app-list-item/index.tsx b/src/components/app-list-item/index.tsx index e2ff2130d..352c08081 100644 --- a/src/components/app-list-item/index.tsx +++ b/src/components/app-list-item/index.tsx @@ -52,11 +52,13 @@ export type FavouriteClickedHandler = ( ) => void; export interface AppListItemProps { - app: Readonly; + app?: Readonly; handler: FavouriteClickedHandler; isPlaceholder?: boolean; isFavourite?: boolean; showStatus?: boolean; + name: string; + isLoaded: boolean; } const latestJobStatus: Partial< @@ -144,7 +146,7 @@ const AppItemStatus: FunctionComponent = ({ )} - {environmentActiveComponents || latestJob ? ( + {(environmentActiveComponents || latestJob) && ( = ({ }), }} /> - ) : ( - - - )} @@ -198,39 +196,51 @@ export const AppListItem: FunctionComponent = ({ isPlaceholder, isFavourite, showStatus, + name, + isLoaded, }) => (
- +
- {app.name} + {name}
-
- {showStatus && } + {isLoaded && + showStatus && + (app ? ( + + ) : ( + + + + ))}
); AppListItem.propTypes = { - app: PropTypes.object.isRequired as PropTypes.Validator, + app: PropTypes.object as PropTypes.Validator, handler: PropTypes.func.isRequired, isPlaceholder: PropTypes.bool, isFavourite: PropTypes.bool, showStatus: PropTypes.bool, + isLoaded: PropTypes.bool.isRequired, + name: PropTypes.string.isRequired, }; diff --git a/src/components/app-list/index.tsx b/src/components/app-list/index.tsx index 0598dca0c..beb7adc31 100644 --- a/src/components/app-list/index.tsx +++ b/src/components/app-list/index.tsx @@ -1,4 +1,9 @@ -import { Button, CircularProgress, Typography } from '@equinor/eds-core-react'; +import { + Button, + CircularProgress, + Icon, + Typography, +} from '@equinor/eds-core-react'; import { type FunctionComponent, useEffect, useState } from 'react'; import { radixApi, useGetSearchApplicationsQuery } from '../../store/radix-api'; @@ -8,6 +13,7 @@ import AsyncResource from '../async-resource/async-resource'; import PageCreateApplication from '../page-create-application'; import './style.css'; +import { refresh } from '@equinor/eds-icons'; import { isEqual, uniq } from 'lodash'; import useLocalStorage from '../../effects/use-local-storage'; import { pollingInterval } from '../../store/defaults'; @@ -23,22 +29,34 @@ const LoadingCards: FunctionComponent<{ amount: number }> = ({ amount }) => ( app={{ name: 'dummy' }} handler={(e) => e.preventDefault()} isPlaceholder + name={''} + isLoaded={false} /> ))} ); +const isArrayOfStrings = (variable: unknown): variable is string[] => { + return ( + Array.isArray(variable) && + variable.every((item) => typeof item === 'string') + ); +}; + export default function AppList() { const [randomPlaceholderCount] = useState(Math.floor(Math.random() * 5) + 3); + const [favourites, setFavourites] = useLocalStorage>( 'favouriteApplications', - [] + [], + isArrayOfStrings ); + const [knownAppNames, setKnownAppNames] = useLocalStorage>( 'knownApplications', - [] + [], + isArrayOfStrings ); - const [refreshApps, appsState] = radixApi.endpoints.showApplications.useLazyQuery({}); @@ -73,18 +91,9 @@ export default function AppList() { isFavourite: favourites?.includes(appName), })); - const favouriteApps = dataSorter( - [ - ...(favsData ?? []) - .filter(({ name }) => favourites?.includes(name)) - .map((favApp) => ({ isFavourite: true, ...favApp }) as const), - ...knownApps, - ].filter( - (app, i, arr) => - app.isFavourite && arr.findIndex((x) => x.name === app.name) === i // remove non-favourites and duplicates - ), - [(x, y) => sortCompareString(x.name, y.name)] - ); + const favouriteNames = dataSorter(favourites ?? [], [ + (x, y) => sortCompareString(x, y), + ]); // remove from know app names previously favorite knownApps, which do not currently exist useEffect(() => { @@ -116,42 +125,28 @@ export default function AppList() {
Favourites -
- -
+
- {favsState.isLoading ? ( -
- Loading favorites… -
- ) : favouriteApps?.length > 0 ? ( + {favouriteNames?.length > 0 ? ( <>
- 0), - }} - loadingContent={ - - } - > -
- {favouriteApps.map((app, i) => ( - { - changeFavouriteApplication(app.name, false); - e.preventDefault(); - }} - isFavourite - showStatus - /> - ))} -
-
+
+ {favouriteNames.map((appName) => ( + a.name === appName)} + handler={(e) => { + changeFavouriteApplication(appName, false); + e.preventDefault(); + }} + isFavourite + showStatus + isLoaded={favsState.isSuccess} + name={appName} + /> + ))} +
) : ( @@ -167,6 +162,8 @@ export default function AppList() { )}
@@ -198,15 +196,17 @@ export default function AppList() { } >
- {knownApps.map((app, i) => ( + {knownApps.map((app) => ( { changeFavouriteApplication(app.name, !app.isFavourite); e.preventDefault(); }} isFavourite={app.isFavourite} + name={app.name} + isLoaded={true} /> ))}
diff --git a/src/components/app-list/style.css b/src/components/app-list/style.css index 20ce210d4..ab69943d9 100644 --- a/src/components/app-list/style.css +++ b/src/components/app-list/style.css @@ -4,7 +4,7 @@ } .app-list__header { display: grid; - grid-template-columns: repeat(2, 1fr); + grid-template-columns: repeat(auto-fit, minmax(250px, 1fr)); align-items: center; } .app-list .app-list--section { diff --git a/src/components/page-create-application/index.tsx b/src/components/page-create-application/index.tsx index 4b78a12e8..1340d034b 100644 --- a/src/components/page-create-application/index.tsx +++ b/src/components/page-create-application/index.tsx @@ -35,7 +35,7 @@ export default function PageCreateApplication() { return ( <>