Skip to content

Commit

Permalink
refactor: review updates
Browse files Browse the repository at this point in the history
  • Loading branch information
canerakdas committed Feb 21, 2024
1 parent 15f273e commit 0df1d1a
Show file tree
Hide file tree
Showing 6 changed files with 154 additions and 127 deletions.
13 changes: 6 additions & 7 deletions components/Downloads/Release/BitnessDropdown.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import semVer from 'semver';
import Select from '@/components/Common/Select';
import { useDetectOS } from '@/hooks/react-client';
import { useReleaseContext } from '@/providers/releaseProvider';
import { getBitnessItems } from '@/util/downloadUtils';
import { bitnessItems, formatDropdownItems } from '@/util/downloadUtils';

const BitnessDropdown: FC = () => {
const { bitness: userBitness } = useDetectOS();
Expand All @@ -24,14 +24,13 @@ const BitnessDropdown: FC = () => {

return (
<Select
values={[
{
items: getBitnessItems(os, hasWindowsArm64),
},
]}
values={formatDropdownItems({
items: bitnessItems[os],
disabledItems: !hasWindowsArm64 && os === 'WIN' ? ['arm64'] : [],
})}
defaultValue={String(bitness)}
onChange={setBitness}
inline
inline={true}
className="min-w-20"
/>
);
Expand Down
4 changes: 2 additions & 2 deletions components/Downloads/Release/NpmVersion.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import type { FC } from 'react';

import { useReleaseContext } from '@/providers/releaseProvider';

const ReleaseNpm: FC = () => {
const NpmVersion: FC = () => {
const {
state: {
release: { npm },
Expand All @@ -14,4 +14,4 @@ const ReleaseNpm: FC = () => {
return <>{npm}</>;
};

export default ReleaseNpm;
export default NpmVersion;
52 changes: 14 additions & 38 deletions components/Downloads/Release/OperatingSystemDropdown.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
'use client';

import type { FC } from 'react';
import { useEffect, useMemo } from 'react';
import { useEffect } from 'react';

import Select from '@/components/Common/Select';
import Apple from '@/components/Icons/Platform/Apple';
Expand All @@ -10,7 +10,10 @@ import Microsoft from '@/components/Icons/Platform/Microsoft';
import { useDetectOS } from '@/hooks/react-client';
import { useReleaseContext } from '@/providers/releaseProvider';
import type { UserOS } from '@/types/userOS';
import { OperatingSystem } from '@/util/downloadUtils';
import {
formatDropdownItems,
operatingSystemItems,
} from '@/util/downloadUtils';

type OperatingSystemDropdownProps = { exclude: Array<UserOS> };

Expand All @@ -27,47 +30,20 @@ const OperatingSystemDropdown: FC<OperatingSystemDropdownProps> = ({
setOs(userOS);
}, [setOs, userOS]);

const items = useMemo(
() =>
[
{
label: OperatingSystem.WIN,
value: 'WIN' as UserOS,
iconImage: <Microsoft width={16} height={16} />,
},
{
label: OperatingSystem.MAC,
value: 'MAC' as UserOS,
iconImage: <Apple width={16} height={16} />,
},
{
label: OperatingSystem.LINUX,
value: 'LINUX' as UserOS,
iconImage: <Linux width={16} height={16} />,
},
].map(item => {
if (exclude.indexOf(item.value) >= 0) {
return {
...item,
disabled: true,
};
}

return item;
}),
[exclude]
);

return (
<Select
values={[
{
items: items,
values={formatDropdownItems({
items: operatingSystemItems,
disabledItems: exclude,
icons: {
WIN: <Microsoft width={16} height={16} />,
MAC: <Apple width={16} height={16} />,
LINUX: <Linux width={16} height={16} />,
},
]}
})}
defaultValue={os}
onChange={(value: string) => setOs(value as UserOS)}
inline
inline={true}
className="min-w-28"
/>
);
Expand Down
40 changes: 11 additions & 29 deletions components/Downloads/Release/PlatformDropdown.tsx
Original file line number Diff line number Diff line change
@@ -1,53 +1,35 @@
'use client';

import type { FC } from 'react';
import { useMemo } from 'react';

import Select from '@/components/Common/Select';
import Generic from '@/components/Icons/Platform/Generic';
import Homebrew from '@/components/Icons/Platform/Homebrew';
import NVM from '@/components/Icons/Platform/NVM';
import { useReleaseContext } from '@/providers/releaseProvider';
import { formatDropdownItems, platformItems } from '@/util/downloadUtils';

const PlatformDropdown: FC = () => {
const {
state: { platform },
dispatch: { setPlatform },
} = useReleaseContext();

const items = useMemo(
() => [
{
label: 'NVM',
value: 'NVM',
iconImage: <NVM width={16} height={16} />,
},
{
label: 'Brew',
value: 'BREW',
iconImage: <Homebrew width={16} height={16} />,
},
{
label: 'fvm',
value: 'FWM',
iconImage: (
<Generic className="dark:stroke-neutral-600" width={16} height={16} />
),
},
],
[]
);

return (
<Select
values={[
{
items: items,
values={formatDropdownItems({
items: platformItems,
icons: {
NVM: <NVM width={16} height={16} />,
BREW: <Homebrew width={16} height={16} />,
},
]}
defaultIcon: (
<Generic className="dark:stroke-neutral-600" width={16} height={16} />
),
})}
defaultValue={platform}
onChange={setPlatform}
inline
inline={true}
className="min-w-24"
/>
);
Expand Down
66 changes: 47 additions & 19 deletions util/__tests__/downloadUtils.test.mjs
Original file line number Diff line number Diff line change
@@ -1,39 +1,67 @@
import {
getBitnessItems,
getDownloadCategory,
mapCategoriesToTabs,
formatDropdownItems,
} from '@/util/downloadUtils';

describe('getBitnessItems', () => {
it('should return correct bitness items for Windows with ARM64', () => {
const result = getBitnessItems('WIN', true);
describe('formatDropdownItems', () => {
it('should format dropdown items correctly', () => {
const items = [
{ value: 'item1', label: 'Item 1' },
{ value: 'item2', label: 'Item 2' },
];
const disabledItems = ['item2'];
const icons = { item1: 'icon' };
const defaultIcon = 'defaultIcon';

const result = formatDropdownItems({
items: items,
disabledItems: disabledItems,
icons: icons,
defaultIcon: defaultIcon,
});

expect(result).toEqual([
{ label: '32-bit', value: '86' },
{ label: '64-bit', value: '64' },
{ label: 'ARM64', value: 'arm64', disabled: false },
{ value: 'item1', label: 'Item 1', disabled: false, iconImage: 'icon' },
{
value: 'item2',
label: 'Item 2',
disabled: true,
iconImage: 'defaultIcon',
},
]);
});

it('should return correct bitness items for Windows without ARM64', () => {
const result = getBitnessItems('WIN', false);
it('should mark all items as disabled when all items are in the disabledItems list', () => {
const items = [
{ value: 'item1', label: 'Item 1' },
{ value: 'item2', label: 'Item 2' },
];
const disabledItems = ['item1', 'item2'];

const result = formatDropdownItems({
items: items,
disabledItems: disabledItems,
});

expect(result).toEqual([
{ label: '32-bit', value: '86' },
{ label: '64-bit', value: '64' },
{ label: 'ARM64', value: 'arm64', disabled: true },
{ value: 'item1', label: 'Item 1', disabled: true },
{ value: 'item2', label: 'Item 2', disabled: true },
]);
});

it('should return correct bitness items for MacOs', () => {
const result = getBitnessItems('MAC', false);
it('should not mark any items as disabled when disabledItems list is empty', () => {
const items = [
{ value: 'item1', label: 'Item 1' },
{ value: 'item2', label: 'Item 2' },
];

expect(result).toEqual([{ label: '64-bit / ARM64', value: '64' }]);
});
const result = formatDropdownItems({ items: items });

it('should return empty array for Linux and Other', () => {
expect(getBitnessItems('LINUX', false)).toEqual([]);
expect(getBitnessItems('OTHER', false)).toEqual([]);
expect(result).toEqual([
{ value: 'item1', label: 'Item 1', disabled: false },
{ value: 'item2', label: 'Item 2', disabled: false },
]);
});
});

Expand Down
106 changes: 74 additions & 32 deletions util/downloadUtils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,45 +4,87 @@ import type { UserOS } from '@/types/userOS';
// A utility enum to help convert `userOs` data type to user-readable format
export enum OperatingSystem {
WIN = 'Windows',
MAC = 'MacOs',
MAC = 'MacOS',
LINUX = 'Linux',
OTHER = 'Other',
}

// A utility for creating and filtering bitness items updates the diabled status
// based on `hasWindowsArm64` status.
// @todo In case this method needs more than one filter, an exclude method can
// be written
export const getBitnessItems = (os: UserOS, hasWindowsArm64: boolean) => {
const bitnessMap = {
WIN: [
{
label: '32-bit',
value: '86',
},
{
label: '64-bit',
value: '64',
},
{
label: 'ARM64',
value: 'arm64',
disabled: !hasWindowsArm64,
},
],
MAC: [
{
label: '64-bit / ARM64',
value: '64',
},
],
LINUX: [],
OTHER: [],
};
export const operatingSystemItems = [
{
label: OperatingSystem.WIN,
value: 'WIN' as UserOS,
},
{
label: OperatingSystem.MAC,
value: 'MAC' as UserOS,
},
{
label: OperatingSystem.LINUX,
value: 'LINUX' as UserOS,
},
];

return bitnessMap[os];
export const platformItems = [
{
label: 'NVM',
value: 'NVM',
},
{
label: 'Brew',
value: 'BREW',
},
{
label: 'fvm',
value: 'FWM',
},
];

export const bitnessItems = {
WIN: [
{
label: '32-bit',
value: '86',
},
{
label: '64-bit',
value: '64',
},
{
label: 'ARM64',
value: 'arm64',
},
],
MAC: [
{
label: '64-bit / ARM64',
value: '64',
},
],
LINUX: [],
OTHER: [],
};

type formatDropdownItemsType = {
items: Array<{ label: string; value: string }>;
disabledItems?: Array<string>;
icons?: Record<string, JSX.Element>;
defaultIcon?: JSX.Element;
};

// Formats the dropdown items to be used in the `Select` component in the
// download page and adds the icons, and disabled status to the dropdown items.
export const formatDropdownItems = ({
items,
disabledItems = [],
icons = {},
defaultIcon,
}: formatDropdownItemsType) =>
items.map(item => ({
...item,
disabled: disabledItems.includes(item.value),
iconImage: icons[item.value] || defaultIcon,
}));

// Returns the page, category and subCategoy information to be used in the page
// from the pathname information on the download pages.
export const getDownloadCategory = (pathname: string) => {
Expand Down

0 comments on commit 0df1d1a

Please sign in to comment.