Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update next.js #610

Merged
merged 15 commits into from
Jun 5, 2023
1 change: 0 additions & 1 deletion frontend/jest/test.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ module.exports = createConfig({
names.
*/
'^.+\\.module\\.scss$': 'identity-obj-proxy',
'^@/i18n/(.*)$': '<rootDir>/i18n/$1',
'^@/(.*)$': '<rootDir>/src/$1',
},
});
19 changes: 8 additions & 11 deletions frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -70,9 +70,6 @@
"// Type checks codebase with TypeScript": "",
"type-check": "tsc -p tsconfig.json --noEmit"
},
"resolutions": {
"@types/react": "17.0.44"
},
"dependencies": {
"@emotion/css": "11.10.5",
"@emotion/react": "11.10.5",
Expand All @@ -98,14 +95,14 @@
"glob": "8.0.1",
"hast-util-sanitize": "4.0.0",
"lodash": "4.17.21",
"next": "12.1.1",
"next": "^13.4.4",
"next-dynamic-loading-props": "0.1.1",
"next-i18next": "11.0.0",
"next-mdx-remote": "4.0.3",
"next-plausible": "3.1.9",
"next-i18next": "13.2.2",
"next-mdx-remote": "4.4.1",
"next-plausible": "3.7.2",
"prism-react-renderer": "1.3.1",
"react": "18.1.0",
"react-dom": "18.1.0",
"react": "18.2.0",
"react-dom": "18.2.0",
"react-highlight-words": "0.18.0",
"react-i18next": "11.16.7",
"react-icons": "^4.7.1",
Expand Down Expand Up @@ -136,7 +133,7 @@
},
"devDependencies": {
"@babel/core": "7.17.10",
"@next/eslint-plugin-next": "12.1.6",
"@next/eslint-plugin-next": "13.4.4",
"@playwright/test": "^1.29.2",
"@tailwindcss/typography": "0.5.2",
"@testing-library/jest-dom": "5.16.4",
Expand All @@ -148,7 +145,7 @@
"@types/jest": "27.5.0",
"@types/lodash-es": "4.17.6",
"@types/node": "^18.11.9",
"@types/react": "17.0.44",
"@types/react": "18.0.26",
"@types/react-highlight-words": "0.16.4",
"@types/react-i18next": "8.1.0",
"@types/string-similarity": "4.0.0",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,14 @@ export function HighlightedCountText({ count = 0, isLoading, i18nKey }: Props) {

return (
<span className="!font-medium inline-flex items-center mr-2">
{isLoading ? <Skeleton className="mr-2" width={32} /> : formattedInstalls}{' '}
{t(i18nKey, { count })}
<>
{isLoading ? (
<Skeleton className="mr-2" width={32} />
) : (
formattedInstalls
)}{' '}
{t(i18nKey, { count })}
</>
</span>
);
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import Skeleton from '@mui/material/Skeleton';
import dayjs from 'dayjs';
import { useTranslation } from 'next-i18next';
import { ReactNode } from 'react';

import { AreaChart } from '@/components/ActivityDashboard/AreaChart';
import { LineTooltip } from '@/components/ActivityDashboard/AreaChart/LineTooltip';
Expand Down Expand Up @@ -58,7 +59,7 @@ export function MonthlyStatsChart({
startDate={startDate}
>
<section>
<Text variant="bodyS">{t(titleI18nKey)}</Text>
<Text variant="bodyS">{t(titleI18nKey) as ReactNode}</Text>

<div className="flex items-center mt-sds-l">
{isEmpty ? (
Expand Down
5 changes: 3 additions & 2 deletions frontend/src/components/ActivityDashboard/RecentStats.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import dayjs from 'dayjs';
import { useTranslation } from 'next-i18next';
import { ReactNode } from 'react';

import { Text } from '@/components/Text';
import { DateBucketType, useDateBucketType } from '@/hooks';
Expand Down Expand Up @@ -38,10 +39,10 @@ export function RecentStats({
/>
)}

<span className="mr-2">{t(infoI18nKey)}</span>
<span className="mr-2">{t(infoI18nKey) as ReactNode}</span>

{durationI18nKey && (
<span className="!font-medium">{t(durationI18nKey)}</span>
<span className="!font-medium">{t(durationI18nKey) as ReactNode}</span>
)}

{date && !durationI18nKey && (
Expand Down
14 changes: 8 additions & 6 deletions frontend/src/components/ActivityDashboard/TotalStats.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -45,12 +45,14 @@ export function TotalStats({
/>

<span className="mr-2">
{t(infoI18nKey)}{' '}
{t(
dateBucketType === DateBucketType.LessThanAWeek
? 'activity:duration.lessThan'
: 'activity:duration.over',
)}
<>
{t(infoI18nKey)}{' '}
{t(
dateBucketType === DateBucketType.LessThanAWeek
? 'activity:duration.lessThan'
: 'activity:duration.over',
)}
</>
</span>

<FormattedDuration date={date} isLoading={isLoading} />
Expand Down
12 changes: 9 additions & 3 deletions frontend/src/components/CategoryChip/CategoryChip.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,11 @@ function BaseCategoryChip(
className="underline"
href={`/?${STATE_KEY_MAP[dimension] ?? ''}=${term}`}
>
{t(`pluginData:category.labels.${term}` as I18nKeys<'common'>)}
{
t(
`pluginData:category.labels.${term}` as I18nKeys<'common'>,
) as ReactNode
}
</Link>
) : (
<span>{term}</span>
Expand Down Expand Up @@ -96,7 +100,7 @@ function BaseCategoryChip(
)}
>
<span className="font-semibold text-sm">{categoryType}</span>
<span className="text-xs">{tooltipBody}</span>
<span className="text-xs">{tooltipBody as ReactNode}</span>
<span className="text-xs italic">
{t('pluginData:category.clickToAdd')}
</span>
Expand Down Expand Up @@ -157,7 +161,9 @@ function BaseCategoryChip(
}}
label={
<div className="flex items-center space-x-sds-xxs">
<span className="font-semibold space-x-sds-xxs">{chipBody}</span>
<span className="font-semibold space-x-sds-xxs">
{chipBody as ReactNode}
</span>
{isTapDevice ? icon : renderTooltip(icon)}
</div>
}
Expand Down
8 changes: 6 additions & 2 deletions frontend/src/components/CollectionPage/CollectionLinks.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import clsx from 'clsx';
import { useTranslation } from 'next-i18next';
import { ComponentType } from 'react';
import { ComponentType, ReactNode } from 'react';
import { GitHub, OrcID, Twitter, Website } from 'src/components/icons';
import { Link } from 'src/components/Link';
import { Tooltip } from 'src/components/Tooltip';
Expand Down Expand Up @@ -53,6 +53,10 @@ function CollectionLink({ linkKey }: CollectionLinkProps) {
const [tooltip, Icon] = useLinkData(linkKey);
const link = useLink(linkKey);

if (!link) {
return null;
}

return (
<Tooltip
arrow={false}
Expand All @@ -63,7 +67,7 @@ function CollectionLink({ linkKey }: CollectionLinkProps) {
'!text-[#5b5b5b] !text-sds-body-xxs',
),
}}
title={tooltip}
title={tooltip as ReactNode}
placement="bottom"
disableInteractive
leaveDelay={0}
Expand Down
22 changes: 11 additions & 11 deletions frontend/src/components/Link/Link.tsx
Original file line number Diff line number Diff line change
@@ -1,19 +1,21 @@
import NextLink, { LinkProps } from 'next/link';
import { AnchorHTMLAttributes, forwardRef } from 'react';
import NextLink from 'next/link';
import { AnchorHTMLAttributes, ComponentProps, forwardRef } from 'react';
import { Optional } from 'utility-types';

export interface Props extends AnchorHTMLAttributes<HTMLElement> {
linkProps?: LinkProps;
}
type LinkProps = ComponentProps<typeof NextLink>;

export type Props = Optional<LinkProps, 'href'>;

/**
* Component for rendering a Next.js link using an anchor tag. This is mostly
* to allow Next.js to preload routes and for the anchor tag to pass a11y.
*/
export const Link = forwardRef<HTMLAnchorElement, Props>(
({ children, href = '', linkProps = { href }, ...props }, ref) => {
({ children, href = '', ...props }, ref) => {
let newTabProps: AnchorHTMLAttributes<HTMLElement> | undefined;
const url = typeof href === 'string' ? href : href.href;

if (href.startsWith('http://') || href.startsWith('https://')) {
if (url?.startsWith('http://') || url?.startsWith('https://')) {
// For new tabs, add rel=noreferrer for security:
// https://web.dev/external-anchors-use-rel-noopener/#how-to-improve-your-site's-performance-and-prevent-security-vulnerabilities
newTabProps = {
Expand All @@ -23,10 +25,8 @@ export const Link = forwardRef<HTMLAnchorElement, Props>(
}

return (
<NextLink {...linkProps}>
<a href={href} {...props} {...newTabProps} ref={ref}>
{children}
</a>
<NextLink {...props} {...newTabProps} href={href} ref={ref}>
{children}
</NextLink>
);
},
Expand Down
9 changes: 7 additions & 2 deletions frontend/src/components/MDX/MDXLinkNode.tsx
Original file line number Diff line number Diff line change
@@ -1,9 +1,14 @@
import { get } from 'lodash';
import { AnchorHTMLAttributes } from 'react';

import { Link, Props as LinkProps } from '@/components/Link';
import { Link } from '@/components/Link';
import { useLinks } from '@/hooks/useLinks';
import { LinkInfo } from '@/types';

interface MDXLinkNodeProps extends AnchorHTMLAttributes<HTMLAnchorElement> {
newTab?: boolean;
}

/**
* Helper component that renders link nodes for the MDX renderer. If the
* component uses a special hub link key, it will automatically be filled with
Expand All @@ -16,7 +21,7 @@ import { LinkInfo } from '@/types';
* [link to the faq]({FAQ})
* ```
*/
export function MDXLinkNode({ href, ...props }: LinkProps) {
export function MDXLinkNode({ href, ...props }: MDXLinkNodeProps) {
const links = useLinks();

let newHref = decodeURI(href ?? '');
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,13 @@ import {
} from '@testing-library/react';
import { get } from 'lodash';

import homePageI18n from '@/i18n/en/homePage.json';
import pluginDataI18n from '@/i18n/en/pluginPage.json';
import { SearchStoreProvider } from '@/store/search/context';
import { SearchFilterStore } from '@/store/search/filter.store';
import { PluginSearchStore } from '@/store/search/search.store';

// TODO Fix absolute import for jest tests
import homePageI18n from '../../../i18n/en/homePage.json';
import pluginDataI18n from '../../../i18n/en/pluginData.json';
import { PluginComplexFilter } from './PluginComplexFilter';

jest.mock('next-i18next', () => ({
Expand Down
3 changes: 2 additions & 1 deletion frontend/src/components/SearchPage/PluginSortByForm.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import RadioGroup from '@mui/material/RadioGroup';
import clsx from 'clsx';
import { motion } from 'framer-motion';
import { useTranslation } from 'next-i18next';
import { ReactNode } from 'react';
import type { TFuncKey } from 'react-i18next';
import { useSnapshot } from 'valtio';

Expand Down Expand Up @@ -87,7 +88,7 @@ function SortForm() {
color="default"
/>
}
label={t(`homePage:${SORT_BY_LABELS[sortType]}`)}
label={t(`homePage:${SORT_BY_LABELS[sortType]}`) as ReactNode}
/>
</motion.div>
))}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ exports[`<PluginComplexFilter /> should match snapshot 1`] = `
<span
class="font-semibold text-sm"
>
pluginData:labels.operatingSystem
Operating system
</span>
<svg
class="w-4 h-4"
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/components/SitemapPage/SitemapPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ export function SitemapPage({ entries }: { entries: SitemapEntry[] }) {
>
<Text variant="h2">
<Link className="underline" href={categoryToPathMap[category]}>
{t(`common:${category}` as I18nKeys<'common'>)}
{t(`common:${category}` as I18nKeys<'common'>) as string}
</Link>
</Text>

Expand Down
19 changes: 10 additions & 9 deletions frontend/src/constants/i18n.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
import activity from '@/i18n/en/activity.json';
import collections from '@/i18n/en/collections.json';
import common from '@/i18n/en/common.json';
import footer from '@/i18n/en/footer.json';
import homePage from '@/i18n/en/homePage.json';
import pageTitles from '@/i18n/en/pageTitles.json';
import pluginData from '@/i18n/en/pluginData.json';
import pluginPage from '@/i18n/en/pluginPage.json';
import preview from '@/i18n/en/preview.json';
// TODO Fix absolute import for jest tests
import activity from '../../i18n/en/activity.json';
import collections from '../../i18n/en/collections.json';
import common from '../../i18n/en/common.json';
import footer from '../../i18n/en/footer.json';
import homePage from '../../i18n/en/homePage.json';
import pageTitles from '../../i18n/en/pageTitles.json';
import pluginData from '../../i18n/en/pluginData.json';
import pluginPage from '../../i18n/en/pluginPage.json';
import preview from '../../i18n/en/preview.json';

/**
* Dictionary of all i18n resources. This is used for generating type
Expand Down
Loading