Skip to content

Commit

Permalink
refactor: Implement functional code for the 'useFilteredApps' hook (#…
Browse files Browse the repository at this point in the history
…30279)

Co-authored-by: Tiago Evangelista Pinto <[email protected]>
  • Loading branch information
2 people authored and debdutdeb committed Oct 26, 2023
1 parent 7966367 commit 16742dc
Show file tree
Hide file tree
Showing 2 changed files with 71 additions and 67 deletions.
24 changes: 21 additions & 3 deletions apps/meteor/client/views/marketplace/AppsPage/AppsPageContent.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -100,16 +100,34 @@ const AppsPageContent = (): ReactElement => {
}
}, [context, marketplaceApps, installedApps, privateApps]);

const findSort = () => {
const possibleSort = sortFilterStructure.items.find(({ checked }) => checked);

return possibleSort ? possibleSort.id : 'mru';
};

const findPurchaseType = () => {
const possiblePurchaseType = freePaidFilterStructure.items.find(({ checked }) => checked);

return possiblePurchaseType ? possiblePurchaseType.id : 'all';
};

const findStatus = () => {
const possibleStatus = statusFilterStructure.items.find(({ checked }) => checked);

return possibleStatus ? possibleStatus.id : 'all';
};

const [categories, selectedCategories, categoryTagList, onSelected] = useCategories();
const appsResult = useFilteredApps({
appsData: getAppsData(),
text,
current,
itemsPerPage,
categories: useMemo(() => selectedCategories.map(({ label }) => label), [selectedCategories]),
purchaseType: useMemo(() => freePaidFilterStructure.items.find(({ checked }) => checked)?.id, [freePaidFilterStructure]),
sortingMethod: useMemo(() => sortFilterStructure.items.find(({ checked }) => checked)?.id, [sortFilterStructure]),
status: useMemo(() => statusFilterStructure.items.find(({ checked }) => checked)?.id, [statusFilterStructure]),
purchaseType: useMemo(findPurchaseType, [freePaidFilterStructure]),
sortingMethod: useMemo(findSort, [sortFilterStructure]),
status: useMemo(findStatus, [statusFilterStructure]),
context,
});

Expand Down
114 changes: 50 additions & 64 deletions apps/meteor/client/views/marketplace/hooks/useFilteredApps.ts
Original file line number Diff line number Diff line change
Expand Up @@ -33,11 +33,11 @@ export const useFilteredApps = ({
text: string;
current: number;
itemsPerPage: number;
categories?: string[];
purchaseType?: string;
categories: string[];
purchaseType: string;
isEnterpriseOnly?: boolean;
sortingMethod?: string;
status?: string;
sortingMethod: string;
status: string;
context?: string;
}): AsyncState<
{ items: App[] } & { shouldShowSearchText: boolean } & PaginatedResult & { allApps: App[] } & { totalAppsLength: number }
Expand All @@ -48,72 +48,58 @@ export const useFilteredApps = ({
}

const { apps } = appsData.value;

let filtered: App[] = apps;
let shouldShowSearchText = true;

const sortingMethods: Record<string, () => App[]> = {
urf: () =>
filtered.sort(
(firstApp, secondApp) => (secondApp?.appRequestStats?.totalUnseen || 0) - (firstApp?.appRequestStats?.totalUnseen || 0),
),
url: () =>
filtered.sort(
(firstApp, secondApp) => (firstApp?.appRequestStats?.totalUnseen || 0) - (secondApp?.appRequestStats?.totalUnseen || 0),
),
az: () => filtered.sort((firstApp, secondApp) => sortAppsByAlphabeticalOrInverseOrder(firstApp.name, secondApp.name)),
za: () => filtered.sort((firstApp, secondApp) => sortAppsByAlphabeticalOrInverseOrder(secondApp.name, firstApp.name)),
mru: () =>
filtered.sort((firstApp, secondApp) => sortAppsByClosestOrFarthestModificationDate(firstApp.modifiedAt, secondApp.modifiedAt)),
lru: () =>
filtered.sort((firstApp, secondApp) => sortAppsByClosestOrFarthestModificationDate(secondApp.modifiedAt, firstApp.modifiedAt)),
const fallback = (apps: App[]) => apps;

const sortingMethods: Record<string, (apps: App[]) => App[]> = {
urf: (apps: App[]) =>
apps.sort((firstApp, secondApp) => (secondApp?.appRequestStats?.totalUnseen || 0) - (firstApp?.appRequestStats?.totalUnseen || 0)),
url: (apps: App[]) =>
apps.sort((firstApp, secondApp) => (firstApp?.appRequestStats?.totalUnseen || 0) - (secondApp?.appRequestStats?.totalUnseen || 0)),
az: (apps: App[]) => apps.sort((firstApp, secondApp) => sortAppsByAlphabeticalOrInverseOrder(firstApp.name, secondApp.name)),
za: (apps: App[]) => apps.sort((firstApp, secondApp) => sortAppsByAlphabeticalOrInverseOrder(secondApp.name, firstApp.name)),
mru: (apps: App[]) =>
apps.sort((firstApp, secondApp) => sortAppsByClosestOrFarthestModificationDate(firstApp.modifiedAt, secondApp.modifiedAt)),
lru: (apps: App[]) =>
apps.sort((firstApp, secondApp) => sortAppsByClosestOrFarthestModificationDate(secondApp.modifiedAt, firstApp.modifiedAt)),
};

if (context && context === 'enterprise') {
filtered = apps.filter(({ categories }) => categories.includes('Enterprise'));
}

if (sortingMethod) {
filtered = sortingMethods[sortingMethod]();
}

const filterByPurchaseType: Record<string, () => App[]> = {
paid: () => filtered.filter(filterAppsByPaid),
enterprise: () => filtered.filter(filterAppsByEnterprise),
free: () => filtered.filter(filterAppsByFree),
const filterByPurchaseType: Record<string, (apps: App[]) => App[]> = {
all: fallback,
paid: (apps: App[]) => apps.filter(filterAppsByPaid),
enterprise: (apps: App[]) => apps.filter(filterAppsByEnterprise),
free: (apps: App[]) => apps.filter(filterAppsByFree),
};

if (purchaseType && purchaseType !== 'all') {
filtered = filterByPurchaseType[purchaseType]();

if (!filtered.length) shouldShowSearchText = false;
}

if (status && status !== 'all') {
filtered = status === 'enabled' ? filtered.filter(filterAppsByEnabled) : filtered.filter(filterAppsByDisabled);

if (!filtered.length) shouldShowSearchText = false;
}

if (Boolean(categories.length) && Boolean(text)) {
filtered = filtered.filter((app) => filterAppsByCategories(app, categories)).filter(({ name }) => filterAppsByText(name, text));
shouldShowSearchText = true;
}

if (Boolean(categories.length) && !text) {
filtered = filtered.filter((app) => filterAppsByCategories(app, categories));
shouldShowSearchText = false;
}

if (!categories.length && Boolean(text)) {
filtered = filtered.filter(({ name }) => filterAppsByText(name, text));
shouldShowSearchText = true;
}
const filterByStatus: Record<string, (apps: App[]) => App[]> = {
all: fallback,
enabled: (apps: App[]) => apps.filter(filterAppsByEnabled),
disabled: (apps: App[]) => apps.filter(filterAppsByDisabled),
};

if (context && context === 'requested') {
filtered = apps.filter(({ appRequestStats, installed }) => Boolean(appRequestStats) && !installed);
}
const filterByContext: Record<string, (apps: App[]) => App[]> = {
explore: fallback,
installed: fallback,
private: fallback,
enterprise: (apps: App[]) => apps.filter(({ categories }) => categories.includes('Enterprise')),
requested: (apps: App[]) => apps.filter(({ appRequestStats, installed }) => Boolean(appRequestStats) && !installed),
};

type appsFilterFunction = (apps: App[]) => App[];
const pipeAppsFilter =
(...functions: appsFilterFunction[]) =>
(initialValue: App[]) =>
functions.reduce((currentAppsList, currentFilterFunction) => currentFilterFunction(currentAppsList), initialValue);

const filtered = pipeAppsFilter(
context ? filterByContext[context] : fallback,
filterByPurchaseType[purchaseType],
filterByStatus[status],
categories.length ? (apps: App[]) => apps.filter((app) => filterAppsByCategories(app, categories)) : fallback,
text ? (apps: App[]) => apps.filter(({ name }) => filterAppsByText(name, text)) : fallback,
sortingMethods[sortingMethod],
)(apps);

const shouldShowSearchText = !!text;
const total = filtered.length;
const offset = current > total ? 0 : current;
const end = current + itemsPerPage;
Expand Down

0 comments on commit 16742dc

Please sign in to comment.