Skip to content

Commit 7f751fd

Browse files
ovflowdCopilotavivkelleramannnbmuenzenmeyer
authored
chore: upgrade to next 15 (#7155)
Co-authored-by: Claudio Wunder <[email protected]> Co-authored-by: Copilot <[email protected]> Co-authored-by: RedYetiDev <[email protected]> Co-authored-by: Jan Amann <[email protected]> Co-authored-by: Brian Muenzenmeyer <[email protected]>
1 parent fa6fbd9 commit 7f751fd

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

68 files changed

+5391
-11709
lines changed

.gitignore

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,4 @@ cache
3131
# TypeScript
3232
tsconfig.tsbuildinfo
3333

34-
# Sentry Config File
35-
.sentryclirc
36-
3734
dist/

.vscode/settings.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,6 @@
33
"editor.formatOnSave": true,
44
"editor.defaultFormatter": "esbenp.prettier-vscode",
55
"javascript.updateImportsOnFileMove.enabled": "always",
6-
"typescript.updateImportsOnFileMove.enabled": "always"
6+
"typescript.updateImportsOnFileMove.enabled": "always",
7+
"typescript.tsdk": "node_modules/typescript/lib"
78
}

COLLABORATOR_GUIDE.md

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -90,7 +90,6 @@ The Website also uses several other Open Source libraries (not limited to) liste
9090
- We use [Rehype](https://github.com/rehypejs/rehype) and [Remark](https://github.com/remarkjs/remark) to extend MDX functionality
9191
- We use [Storybook](https://storybook.js.org/) for Manual Testing and Visual Regression Tests of our React Components
9292
- Storybook also provides a sandboxed environment, which is very useful whilst for crafting React Components
93-
- We use [Sentry](https://sentry.io/about) for reporting Exceptions and monitoring the performance and reliability of the application
9493

9594
## Code Editing
9695

apps/site/.storybook/main.ts

Lines changed: 31 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,35 +1,38 @@
1-
import type { StorybookConfig } from '@storybook/nextjs';
2-
import classNames from 'classnames';
1+
import { join } from 'node:path';
32

4-
const rootClasses = classNames(
5-
// note: this is hard-coded sadly as next/font can only be loaded within next.js context
6-
'__variable_open-sans-normal',
7-
// note: this is hard-coded sadly as next/font can only be loaded within next.js context
8-
'__variable_ibm-plex-mono-normal'
9-
);
3+
import type { StorybookConfig } from '@storybook/react-webpack5';
4+
5+
const mocksFolder = join(__dirname, '../components/__mocks__');
106

117
const config: StorybookConfig = {
128
stories: ['../components/**/*.stories.tsx'],
139
logLevel: 'error',
1410
staticDirs: ['../public'],
1511
typescript: { reactDocgen: false, check: false },
1612
core: { disableTelemetry: true, disableWhatsNewNotifications: true },
17-
framework: {
18-
name: '@storybook/nextjs',
19-
options: { builder: { useSWC: true } },
20-
},
21-
previewBody:
22-
// This `<style>` is necessary to simulate what `next-themes` (ThemeProvider) does on real applications
23-
// `next-theme` automatically injects the color-scheme based on the system preference or the current applied theme
24-
// on Storybook we don't use `next-theme` as we want to simulate themes
25-
'<style>:root { color-scheme: light; } html[data-theme="dark"] { color-scheme: dark; }</style>' +
26-
// This adds the base styling for dark/light themes within Storybook. This is a Storybook-only style
27-
`<body class="${rootClasses}"></body>`,
13+
framework: '@storybook/react-webpack5',
14+
swc: () => ({ jsc: { transform: { react: { runtime: 'automatic' } } } }),
2815
addons: [
16+
'@storybook/addon-webpack5-compiler-swc',
2917
'@storybook/addon-controls',
3018
'@storybook/addon-interactions',
3119
'@storybook/addon-themes',
3220
'@storybook/addon-viewport',
21+
{
22+
name: '@storybook/addon-styling-webpack',
23+
options: {
24+
rules: [
25+
{
26+
test: /\.css$/,
27+
use: [
28+
'style-loader',
29+
{ loader: 'css-loader', options: { url: false } },
30+
'postcss-loader',
31+
],
32+
},
33+
],
34+
},
35+
},
3336
],
3437
webpack: async config => ({
3538
...config,
@@ -39,7 +42,15 @@ const config: StorybookConfig = {
3942
performance: { hints: false },
4043
// `nodevu` is a Node.js-specific package that requires Node.js modules
4144
// this is incompatible with Storybook. So we just mock the module
42-
resolve: { ...config.resolve, alias: { '@nodevu/core': false } },
45+
resolve: {
46+
...config.resolve,
47+
alias: {
48+
'@nodevu/core': false,
49+
'next-intl/navigation': join(mocksFolder, './next-intl.mjs'),
50+
'@/client-context': join(mocksFolder, './client-context.mjs'),
51+
'@': join(__dirname, '../'),
52+
},
53+
},
4354
// We need to configure `node:` APIs as Externals to WebPack
4455
// since essentially they're not supported on the browser
4556
externals: {
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
<link rel="preconnect" href="https://fonts.googleapis.com" />
2+
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
3+
4+
<link
5+
rel="stylesheet"
6+
href="https://fonts.googleapis.com/css2?family=IBM+Plex+Mono&family=Open+Sans:ital,wght@0,300..800;1,300..800"
7+
/>
8+
9+
<style>
10+
:root {
11+
color-scheme: light;
12+
13+
--font-ibm-plex-mono: 'IBM Plex Mono';
14+
--font-open-sans: 'Open Sans';
15+
}
16+
17+
html[data-theme='dark'] {
18+
color-scheme: dark;
19+
}
20+
</style>

apps/site/.storybook/preview.tsx

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,12 +6,10 @@ import { NextIntlClientProvider } from 'next-intl';
66
import { STORYBOOK_MODES, STORYBOOK_SIZES } from '@/.storybook/constants';
77
import { NotificationProvider } from '@/providers/notificationProvider';
88

9-
import '../next.fonts';
109
import '../styles/index.css';
1110

1211
const preview: Preview = {
1312
parameters: {
14-
nextjs: { router: { basePath: '' }, appDirectory: true },
1513
chromatic: { modes: STORYBOOK_MODES },
1614
viewport: { defaultViewport: 'large', viewports: STORYBOOK_SIZES },
1715
},
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
/**
2+
* This file extends on the `page.tsx` file, which is the default file that is used to render
3+
* the entry points for each locale and then also reused within the [...path] route to render the
4+
* and contains all logic for rendering our dynamic and static routes within the Node.js Website.
5+
*
6+
* Note: that each `page.tsx` should have its own `generateStaticParams` to prevent clash of
7+
* dynamic params, which will lead on static export errors and other sort of issues.
8+
*/
9+
10+
import * as basePage from '@/app/[locale]/page';
11+
import { ENABLE_STATIC_EXPORT } from '@/next.constants.mjs';
12+
import { dynamicRouter } from '@/next.dynamic.mjs';
13+
import { availableLocaleCodes } from '@/next.locales.mjs';
14+
15+
// This is the default Viewport Metadata
16+
// @see https://nextjs.org/docs/app/api-reference/functions/generate-viewport#generateviewport-function
17+
export const generateViewport = basePage.generateViewport;
18+
19+
// This generates each page's HTML Metadata
20+
// @see https://nextjs.org/docs/app/api-reference/functions/generate-metadata
21+
export const generateMetadata = basePage.generateMetadata;
22+
23+
// This provides all the possible paths that can be generated statically
24+
// + provides all the paths that we support on the Node.js Website
25+
export const generateStaticParams = async () => {
26+
const allAvailableRoutes = await Promise.all(
27+
// Gets all mapped routes to the Next.js Routing Engine by Locale
28+
availableLocaleCodes.map(async (locale: string) => {
29+
const routesForLanguage = await dynamicRouter.getRoutesByLanguage(locale);
30+
31+
return routesForLanguage.map(pathname =>
32+
dynamicRouter.mapPathToRoute(locale, pathname)
33+
);
34+
})
35+
);
36+
37+
return ENABLE_STATIC_EXPORT ? allAvailableRoutes.flat().sort() : [];
38+
};
39+
40+
// Enforces that this route is used as static rendering
41+
// Except whenever on the Development mode as we want instant-refresh when making changes
42+
// @see https://nextjs.org/docs/app/api-reference/file-conventions/route-segment-config#dynamic
43+
export const dynamic = 'force-static';
44+
45+
// Ensures that this endpoint is invalidated and re-executed every X minutes
46+
// so that when new deployments happen, the data is refreshed
47+
// @see https://nextjs.org/docs/app/api-reference/file-conventions/route-segment-config#revalidate
48+
export const revalidate = 300;
49+
50+
export default basePage.default;

apps/site/app/[locale]/error.tsx

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,13 @@
11
'use client';
22

33
import { ArrowRightIcon } from '@heroicons/react/24/solid';
4-
import { captureException } from '@sentry/nextjs';
54
import { useTranslations } from 'next-intl';
65
import type { FC } from 'react';
76

87
import Button from '@/components/Common/Button';
98
import GlowingBackdropLayout from '@/layouts/GlowingBackdrop';
109

11-
const ErrorPage: FC<{ error: Error }> = ({ error }) => {
12-
captureException(error);
10+
const ErrorPage: FC<{ error: Error }> = () => {
1311
const t = useTranslations();
1412

1513
return (

apps/site/app/[locale]/feed/[feed]/route.ts

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,20 @@
11
import { NextResponse } from 'next/server';
22

33
import provideWebsiteFeeds from '@/next-data/providers/websiteFeeds';
4-
import { VERCEL_REVALIDATE } from '@/next.constants.mjs';
54
import { siteConfig } from '@/next.json.mjs';
65
import { defaultLocale } from '@/next.locales.mjs';
76

87
// We only support fetching these pages from the /en/ locale code
98
const locale = defaultLocale.code;
109

11-
type StaticParams = { params: { feed: string; locale: string } };
10+
type StaticParams = { params: Promise<{ feed: string; locale: string }> };
1211

1312
// This is the Route Handler for the `GET` method which handles the request
1413
// for the Node.js Website Blog Feeds (RSS)
1514
// @see https://nextjs.org/docs/app/building-your-application/routing/router-handlers
16-
export const GET = async (_: Request, { params }: StaticParams) => {
15+
export const GET = async (_: Request, props: StaticParams) => {
16+
const params = await props.params;
17+
1718
// Generate the Feed for the given feed type (blog, releases, etc)
1819
const websiteFeed = provideWebsiteFeeds(params.feed);
1920

@@ -29,11 +30,9 @@ export const GET = async (_: Request, { params }: StaticParams) => {
2930
export const generateStaticParams = async () =>
3031
siteConfig.rssFeeds.map(feed => ({ feed: feed.file, locale }));
3132

32-
// In this case we want to catch-all possible requests. This is so that if a non defined feed is
33-
// requested we can manually return a 404 response for it instead of having Next.js handle it
34-
// and return our top level custom 404 html page instead
33+
// Enforces that only the paths from `generateStaticParams` are allowed, giving 404 on the contrary
3534
// @see https://nextjs.org/docs/app/api-reference/file-conventions/route-segment-config#dynamicparams
36-
export const dynamicParams = true;
35+
export const dynamicParams = false;
3736

3837
// Enforces that this route is cached and static as much as possible
3938
// @see https://nextjs.org/docs/app/api-reference/file-conventions/route-segment-config#dynamic
@@ -42,4 +41,4 @@ export const dynamic = 'force-static';
4241
// Ensures that this endpoint is invalidated and re-executed every X minutes
4342
// so that when new deployments happen, the data is refreshed
4443
// @see https://nextjs.org/docs/app/api-reference/file-conventions/route-segment-config#revalidate
45-
export const revalidate = VERCEL_REVALIDATE;
44+
export const revalidate = 300;

apps/site/app/[locale]/layout.tsx

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
import { Analytics } from '@vercel/analytics/react';
22
import { SpeedInsights } from '@vercel/speed-insights/next';
33
import classNames from 'classnames';
4-
import { getLocale } from 'next-intl/server';
54
import type { FC, PropsWithChildren } from 'react';
65

76
import BaseLayout from '@/layouts/Base';
@@ -15,13 +14,20 @@ import '@/styles/index.css';
1514

1615
const fontClasses = classNames(IBM_PLEX_MONO.variable, OPEN_SANS.variable);
1716

18-
const RootLayout: FC<PropsWithChildren> = async ({ children }) => {
19-
const locale = await getLocale();
17+
type RotLayoutProps = PropsWithChildren<{ params: { locale: string } }>;
18+
19+
const RootLayout: FC<RotLayoutProps> = async ({ children, params }) => {
20+
const { locale } = await params;
2021

2122
const { langDir, hrefLang } = availableLocalesMap[locale] || defaultLocale;
2223

2324
return (
24-
<html className={fontClasses} dir={langDir} lang={hrefLang}>
25+
<html
26+
className={fontClasses}
27+
dir={langDir}
28+
lang={hrefLang}
29+
suppressHydrationWarning
30+
>
2531
<body suppressHydrationWarning>
2632
<LocaleProvider>
2733
<ThemeProvider>

0 commit comments

Comments
 (0)