Skip to content

Commit

Permalink
feat(pci-common): add 3AZ region and 1AZ chip (#14672)
Browse files Browse the repository at this point in the history
* feat(pci-common): add 3AZ region and 1AZ chip

ref: TAPC-2357, TAPC-2413

Signed-off-by: Simon Chaumet <[email protected]>
Co-authored-by: CDS Translator Agent <[email protected]>
  • Loading branch information
SimonChaumet and ovh-cds authored Jan 14, 2025
1 parent f253154 commit 455b619
Show file tree
Hide file tree
Showing 31 changed files with 866 additions and 144 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { fetchIcebergV6 } from '@ovh-ux/manager-core-api';

export type TRegion = {
name: string;
type: string;
type: 'region' | 'localzone' | 'region-3-az' | string;
status: string;
continentCode: string;
services: {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import { render, screen } from '@testing-library/react';
import { describe, it } from 'vitest';
import { wrapper } from '@/wrapperRenders';
import { Region3AZChip } from '@/components/region-selector/Region3AZChip.component';
import { URL_INFO } from '@/components/region-selector/constants';

describe('Region3AZChip', () => {
it.each([undefined, false, true])(
'should render chip with showTooltip %s with correct texts and links',
(showTooltip: boolean | undefined) => {
render(<Region3AZChip showTooltip={showTooltip} />, { wrapper });

expect(
screen.getByText('pci_project_flavors_zone_3AZ'),
).toBeInTheDocument();

if (showTooltip ?? true) {
expect(
screen.getByText('pci_project_flavors_zone_3AZ_tooltip'),
).toBeInTheDocument();

const link = screen.getByText('pci_project_flavors_zone_tooltip_link');
expect(link).toBeInTheDocument();
expect(link).toHaveAttribute('href', URL_INFO.REGION_3AZ.DEFAULT);
} else {
expect(
screen.queryByText('pci_project_flavors_zone_3AZ_tooltip'),
).not.toBeInTheDocument();
expect(
screen.queryByText('pci_project_flavors_zone_tooltip_link'),
).not.toBeInTheDocument();
}
},
);
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
import { useContext } from 'react';
import { ShellContext } from '@ovh-ux/manager-react-shell-client';
import { useTranslation } from 'react-i18next';
import { URL_INFO } from './constants';
import { RegionChip } from './RegionChip';
import { RegionPopover } from './RegionPopover';

export function Region3AZChip({
showTooltip = true,
}: Readonly<{
showTooltip?: boolean;
}>) {
const { t } = useTranslation('pci-region-selector');
const context = useContext(ShellContext);
const { ovhSubsidiary } = context.environment.getUser();
const documentURL =
URL_INFO.REGION_3AZ[ovhSubsidiary] || URL_INFO.REGION_3AZ.DEFAULT;

const chip = (
<RegionChip
className="chip-3AZ"
title={t('pci_project_flavors_zone_3AZ')}
showTooltipIcon={showTooltip}
onClick={showTooltip ? (event) => event.stopPropagation() : undefined}
/>
);

return showTooltip ? (
<RegionPopover
tooltipUrl={documentURL}
tooltip={t('pci_project_flavors_zone_3AZ_tooltip')}
>
{chip}
</RegionPopover>
) : (
chip
);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
import { OsdsChip, OsdsIcon, OsdsText } from '@ovhcloud/ods-components/react';
import {
JSX,
ODS_CHIP_SIZE,
ODS_ICON_NAME,
ODS_ICON_SIZE,
ODS_TEXT_LEVEL,
ODS_TEXT_SIZE,
} from '@ovhcloud/ods-components';
import { ODS_THEME_COLOR_INTENT } from '@ovhcloud/ods-common-theming';
import React, { HTMLAttributes } from 'react';

export type RegionChipProps = JSX.OsdsChip &
HTMLAttributes<HTMLOsdsChipElement> & {
showTooltipIcon?: boolean;
title: string;
className?: string;
};

export function RegionChip({
showTooltipIcon,
title,
className,
...chipProps
}: RegionChipProps) {
return (
<OsdsChip class={className} size={ODS_CHIP_SIZE.sm} {...chipProps}>
<OsdsText level={ODS_TEXT_LEVEL.body} size={ODS_TEXT_SIZE._500}>
{title}
</OsdsText>
{showTooltipIcon && (
<OsdsIcon
name={ODS_ICON_NAME.HELP}
size={ODS_ICON_SIZE.xs}
className="ml-2"
color={ODS_THEME_COLOR_INTENT.primary}
/>
)}
</OsdsChip>
);
}
Original file line number Diff line number Diff line change
@@ -1,12 +1,107 @@
import { render, screen } from '@testing-library/react';
import { vi } from 'vitest';
import { RegionGlobalzoneChip } from './RegionGlobalzoneChip.component';
import { wrapper } from '@/wrapperRenders';
import { URL_INFO } from '@/components/region-selector/constants';
import { useHas3AZ } from '@/hooks/useHas3AZ/useHas3AZ';
import { useIs1AZ } from '@/hooks/useIs1AZ/useIs1AZ';

vi.mock('@ovh-ux/manager-react-components', async (importOriginal) => {
const module = await importOriginal<
typeof import('@ovh-ux/manager-react-components')
>();
return { ...module, useFeatureAvailability: vi.fn() };
});

vi.mock('@/hooks/useHas3AZ/useHas3AZ');
vi.mock('@/hooks/useIs1AZ/useIs1AZ');

enum ExpectedType {
GLOBAL_REGIONS = 'GLOBAL_REGIONS',
'1AZ_REGIONS' = '1AZ_REGIONS',
}

const EXPECTED_VALUES = {
[ExpectedType.GLOBAL_REGIONS]: {
label: 'pci_project_flavors_zone_global_region',
tooltip: 'pci_project_flavors_zone_globalregions_tooltip',
link: URL_INFO.GLOBAL_REGIONS.DEFAULT,
},
[ExpectedType['1AZ_REGIONS']]: {
label: 'pci_project_flavors_zone_1AZ',
tooltip: 'pci_project_flavors_zone_1AZ_with_3AZ_tooltip',
link: URL_INFO['1AZ_REGIONS'].DEFAULT,
},
};

describe('RegionGlobalzoneChip', () => {
it('renders chip with correct text', () => {
render(<RegionGlobalzoneChip />, { wrapper });
expect(
screen.getByText('pci_project_flavors_zone_global_region'),
).toBeInTheDocument();
});
it.each([
[undefined, undefined, ExpectedType.GLOBAL_REGIONS],
[undefined, false, ExpectedType.GLOBAL_REGIONS],
[undefined, true, ExpectedType['1AZ_REGIONS']],
[false, undefined, ExpectedType.GLOBAL_REGIONS],
[false, false, ExpectedType.GLOBAL_REGIONS],
[false, true, ExpectedType['1AZ_REGIONS']],
[true, undefined, ExpectedType.GLOBAL_REGIONS],
[true, false, ExpectedType.GLOBAL_REGIONS],
[true, true, ExpectedType['1AZ_REGIONS']],
])(
'should render chip with showTooltip %s show1AZ %s with correct texts and links',
(
showTooltip: boolean | undefined,
show1AZ: boolean | undefined,
expectedType,
) => {
const expected = EXPECTED_VALUES[expectedType];

vi.mocked(useIs1AZ).mockReturnValue(show1AZ);

render(<RegionGlobalzoneChip showTooltip={showTooltip} />, { wrapper });

expect(screen.getByText(expected.label)).toBeInTheDocument();

if (showTooltip ?? true) {
expect(screen.getByText(expected.tooltip)).toBeInTheDocument();

const link = screen.getByText('pci_project_flavors_zone_tooltip_link');
expect(link).toBeInTheDocument();
expect(link).toHaveAttribute('href', expected.link);
} else {
expect(screen.queryByText(expected.tooltip)).not.toBeInTheDocument();
expect(
screen.queryByText('pci_project_flavors_zone_tooltip_link'),
).not.toBeInTheDocument();
}
},
);

it.each([
['render', true, false],
['not render', true, true],
['not render', false, true],
['not render', false, false],
])(
'should %s 3AZ tooltip text when feature availability is %s and 3AZ availability is %s',
(expected: string, show1AZ: boolean, has3AZ: boolean) => {
vi.mocked(useIs1AZ).mockReturnValue(show1AZ);

vi.mocked(useHas3AZ).mockReturnValue(has3AZ);

render(<RegionGlobalzoneChip />, { wrapper });

if (expected === 'render') {
expect(
screen.getByText('pci_project_flavors_zone_1AZ_with_3AZ_tooltip'),
).toBeInTheDocument();
} else if (show1AZ) {
expect(
screen.queryByText('pci_project_flavors_zone_1AZ_tooltip'),
).toBeInTheDocument();
} else {
expect(
screen.queryByText('pci_project_flavors_zone_globalregions_tooltip'),
).toBeInTheDocument();
}
},
);
});
Original file line number Diff line number Diff line change
@@ -1,72 +1,53 @@
import React, { useContext } from 'react';
import { Links, LinkType } from '@ovh-ux/manager-react-components';
import { ODS_THEME_COLOR_INTENT } from '@ovhcloud/ods-common-theming';
import { ShellContext } from '@ovh-ux/manager-react-shell-client';
import {
ODS_CHIP_SIZE,
ODS_ICON_NAME,
ODS_ICON_SIZE,
ODS_TEXT_LEVEL,
ODS_TEXT_SIZE,
} from '@ovhcloud/ods-components';
import {
OsdsChip,
OsdsIcon,
OsdsPopover,
OsdsPopoverContent,
OsdsText,
} from '@ovhcloud/ods-components/react';
import { OdsHTMLAnchorElementTarget } from '@ovhcloud/ods-common-core';
import { useTranslation } from 'react-i18next';
import { URL_INFO } from './constants';
import { useHas3AZ } from '../../hooks/useHas3AZ/useHas3AZ';
import { useIs1AZ } from '../../hooks/useIs1AZ/useIs1AZ';
import { RegionChip } from './RegionChip';
import { RegionPopover } from './RegionPopover';

export function RegionGlobalzoneChip() {
export function RegionGlobalzoneChip({
showTooltip = true,
}: Readonly<{
showTooltip?: boolean;
}>) {
const { t } = useTranslation('pci-region-selector');
const is1AZ = useIs1AZ();
const context = useContext(ShellContext);
const { ovhSubsidiary } = context.environment.getUser();
const getDocumentUrl = (linkType: string) =>
URL_INFO[linkType as keyof typeof URL_INFO][ovhSubsidiary] ||
URL_INFO[linkType as keyof typeof URL_INFO].DEFAULT;

return (
<OsdsPopover>
<span slot="popover-trigger">
<OsdsChip
color={ODS_THEME_COLOR_INTENT.primary}
size={ODS_CHIP_SIZE.sm}
onClick={(event) => event.stopPropagation()}
>
<OsdsText
color={ODS_THEME_COLOR_INTENT.primary}
level={ODS_TEXT_LEVEL.body}
size={ODS_TEXT_SIZE._500}
>
{t('pci_project_flavors_zone_global_region')}
</OsdsText>
<OsdsIcon
name={ODS_ICON_NAME.HELP}
size={ODS_ICON_SIZE.xs}
className="ml-2"
color={ODS_THEME_COLOR_INTENT.primary}
/>
</OsdsChip>
</span>
<OsdsPopoverContent>
<OsdsText
color={ODS_THEME_COLOR_INTENT.text}
level={ODS_TEXT_LEVEL.body}
>
{t('pci_project_flavors_zone_globalregions_tooltip')}
</OsdsText>
&nbsp;
<Links
tab-index="-1"
label={t('pci_project_flavors_zone_tooltip_link')}
type={LinkType.external}
target={OdsHTMLAnchorElementTarget._blank}
href={getDocumentUrl('GLOBAL_REGIONS')}
/>
</OsdsPopoverContent>
</OsdsPopover>
const linkType = is1AZ ? '1AZ_REGIONS' : 'GLOBAL_REGIONS';
const tooltipUrl =
URL_INFO[linkType][ovhSubsidiary] || URL_INFO[linkType].DEFAULT;

const has3AZ = useHas3AZ();

const chip = (
<RegionChip
showTooltipIcon={showTooltip}
title={t(`pci_project_flavors_zone_${is1AZ ? '1AZ' : 'global_region'}`)}
className="chip-1AZ"
onClick={showTooltip ? (event) => event.stopPropagation() : undefined}
/>
);

return showTooltip ? (
<RegionPopover
tooltipUrl={tooltipUrl}
tooltip={
is1AZ && !has3AZ
? t('pci_project_flavors_zone_1AZ_with_3AZ_tooltip')
: t(
`pci_project_flavors_zone_${
is1AZ ? '1AZ' : 'globalregions'
}_tooltip`,
)
}
>
{chip}
</RegionPopover>
) : (
chip
);
}
Loading

0 comments on commit 455b619

Please sign in to comment.