From 83f8ea6652a6cdf4e1c3f83b94f02e9daf70fa5e Mon Sep 17 00:00:00 2001 From: Rob Stanford Date: Mon, 26 Jun 2023 11:00:27 +0100 Subject: [PATCH 1/7] fix: use default react resolution for falsy env var --- packages/runtime/src/templates/requireHooks.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/runtime/src/templates/requireHooks.ts b/packages/runtime/src/templates/requireHooks.ts index 99cfc046cf..a78edcbe9f 100644 --- a/packages/runtime/src/templates/requireHooks.ts +++ b/packages/runtime/src/templates/requireHooks.ts @@ -103,7 +103,7 @@ export const applyRequireHooks = () => { isMain: boolean, options: any, ) { - const reactMode = process.env.__NEXT_PRIVATE_PREBUNDLED_REACT ?? 'default' + const reactMode = process.env.__NEXT_PRIVATE_PREBUNDLED_REACT || 'default' const resolvedRequest = hooks.get(reactMode)?.get(request) ?? request return originalResolveFilename.call(mod, resolvedRequest, parent, isMain, options) From 34411501b64306285d06f1f8290ae58ede865381 Mon Sep 17 00:00:00 2001 From: Rob Stanford Date: Mon, 26 Jun 2023 17:03:59 +0100 Subject: [PATCH 2/7] fix: ignore react require hooks that don't resolve --- .../runtime/src/templates/requireHooks.ts | 143 +++++++++--------- 1 file changed, 73 insertions(+), 70 deletions(-) diff --git a/packages/runtime/src/templates/requireHooks.ts b/packages/runtime/src/templates/requireHooks.ts index a78edcbe9f..9633f57656 100644 --- a/packages/runtime/src/templates/requireHooks.ts +++ b/packages/runtime/src/templates/requireHooks.ts @@ -11,86 +11,89 @@ const resolveFilename = (mod as any)._resolveFilename const requireHooks = new Map>() export const overrideRequireHooks = (config: NextConfig) => { - // we may have changed the working directory in the handler - const opts = { - paths: [process.cwd()], - } + setRequireHooks(config) + resolveRequireHooks() +} +const setRequireHooks = (config: NextConfig) => { requireHooks.set( 'default', new Map([ - ['react', require.resolve(`react`, opts)], - ['react/jsx-runtime', require.resolve(`react/jsx-runtime`, opts)], + ['react', `react`], + ['react/jsx-runtime', `react/jsx-runtime`], ]), ) if (config.experimental.appDir) { - requireHooks.set( - 'next', - new Map([ - ['react', require.resolve(`next/dist/compiled/react`, opts)], - ['react/jsx-runtime', require.resolve(`next/dist/compiled/react/jsx-runtime`, opts)], - ['react/jsx-dev-runtime', require.resolve(`next/dist/compiled/react/jsx-dev-runtime`, opts)], - ['react-dom', require.resolve(`next/dist/compiled/react-dom/server-rendering-stub`, opts)], - ['react-dom/client', require.resolve(`next/dist/compiled/react-dom/client`, opts)], - ['react-dom/server', require.resolve(`next/dist/compiled/react-dom/server`, opts)], - ['react-dom/server.browser', require.resolve(`next/dist/compiled/react-dom/server.browser`, opts)], - ['react-dom/server.edge', require.resolve(`next/dist/compiled/react-dom/server.edge`, opts)], - [ - 'react-server-dom-webpack/client', - require.resolve(`next/dist/compiled/react-server-dom-webpack/client`, opts), - ], - [ - 'react-server-dom-webpack/client.edge', - require.resolve(`next/dist/compiled/react-server-dom-webpack/client.edge`, opts), - ], - [ - 'react-server-dom-webpack/server.edge', - require.resolve(`next/dist/compiled/react-server-dom-webpack/server.edge`, opts), - ], - [ - 'react-server-dom-webpack/server.node', - require.resolve(`next/dist/compiled/react-server-dom-webpack/server.node`, opts), - ], - ['styled-jsx', require.resolve('styled-jsx', opts)], - ['styled-jsx/style', require.resolve('styled-jsx/style', opts)], - ]), - ) + if (config.experimental.serverActions) { + requireHooks.set( + 'experimental', + new Map([ + ['react', `next/dist/compiled/react-experimental`], + ['react/jsx-runtime', `next/dist/compiled/react-experimental/jsx-runtime`], + ['react/jsx-dev-runtime', `next/dist/compiled/react-experimental/jsx-dev-runtime`], + ['react-dom', `next/dist/compiled/react-dom-experimental/server-rendering-stub`], + ['react-dom/client', `next/dist/compiled/react-dom-experimental/client`], + ['react-dom/server', `next/dist/compiled/react-dom-experimental/server`], + ['react-dom/server.browser', `next/dist/compiled/react-dom-experimental/server.browser`], + ['react-dom/server.edge', `next/dist/compiled/react-dom-experimental/server.edge`], + ['react-server-dom-webpack/client', `next/dist/compiled/react-server-dom-webpack-experimental/client`], + [ + 'react-server-dom-webpack/client.edge', + `next/dist/compiled/react-server-dom-webpack-experimental/client.edge`, + ], + [ + 'react-server-dom-webpack/server.edge', + `next/dist/compiled/react-server-dom-webpack-experimental/server.edge`, + ], + [ + 'react-server-dom-webpack/server.node', + `next/dist/compiled/react-server-dom-webpack-experimental/server.node`, + ], + ['styled-jsx', 'styled-jsx'], + ['styled-jsx/style', 'styled-jsx/style'], + ]), + ) + } else { + requireHooks.set( + 'next', + new Map([ + ['react', `next/dist/compiled/react`], + ['react/jsx-runtime', `next/dist/compiled/react/jsx-runtime`], + ['react/jsx-dev-runtime', `next/dist/compiled/react/jsx-dev-runtime`], + ['react-dom', `next/dist/compiled/react-dom/server-rendering-stub`], + ['react-dom/client', `next/dist/compiled/react-dom/client`], + ['react-dom/server', `next/dist/compiled/react-dom/server`], + ['react-dom/server.browser', `next/dist/compiled/react-dom/server.browser`], + ['react-dom/server.edge', `next/dist/compiled/react-dom/server.edge`], + ['react-server-dom-webpack/client', `next/dist/compiled/react-server-dom-webpack/client`], + ['react-server-dom-webpack/client.edge', `next/dist/compiled/react-server-dom-webpack/client.edge`], + ['react-server-dom-webpack/server.edge', `next/dist/compiled/react-server-dom-webpack/server.edge`], + ['react-server-dom-webpack/server.node', `next/dist/compiled/react-server-dom-webpack/server.node`], + ['styled-jsx', 'styled-jsx'], + ['styled-jsx/style', 'styled-jsx/style'], + ]), + ) + } } +} - if (config.experimental.serverActions) { - requireHooks.set( - 'experimental', - new Map([ - ['react', require.resolve(`next/dist/compiled/react-experimental`, opts)], - ['react/jsx-runtime', require.resolve(`next/dist/compiled/react-experimental/jsx-runtime`, opts)], - ['react/jsx-dev-runtime', require.resolve(`next/dist/compiled/react-experimental/jsx-dev-runtime`, opts)], - ['react-dom', require.resolve(`next/dist/compiled/react-dom-experimental/server-rendering-stub`, opts)], - ['react-dom/client', require.resolve(`next/dist/compiled/react-dom-experimental/client`, opts)], - ['react-dom/server', require.resolve(`next/dist/compiled/react-dom-experimental/server`, opts)], - ['react-dom/server.browser', require.resolve(`next/dist/compiled/react-dom-experimental/server.browser`, opts)], - ['react-dom/server.edge', require.resolve(`next/dist/compiled/react-dom-experimental/server.edge`, opts)], - [ - 'react-server-dom-webpack/client', - require.resolve(`next/dist/compiled/react-server-dom-webpack-experimental/client`, opts), - ], - [ - 'react-server-dom-webpack/client.edge', - require.resolve(`next/dist/compiled/react-server-dom-webpack-experimental/client.edge`, opts), - ], - [ - 'react-server-dom-webpack/server.edge', - require.resolve(`next/dist/compiled/react-server-dom-webpack-experimental/server.edge`, opts), - ], - [ - 'react-server-dom-webpack/server.node', - require.resolve(`next/dist/compiled/react-server-dom-webpack-experimental/server.node`, opts), - ], - ['styled-jsx', require.resolve('styled-jsx', opts)], - ['styled-jsx/style', require.resolve('styled-jsx/style', opts)], - ]), - ) - } +const resolveRequireHooks = () => { + // we may have changed the working directory in the handler + const opts = { paths: [process.cwd()] } + + // resolve require hooks with module paths + requireHooks.forEach((mode) => { + mode.forEach((hook, path) => { + try { + const resolvedPath = require.resolve(path, opts) + mode.set(hook, resolvedPath) + } catch { + // ignore + mode.delete(hook) + } + }) + }) } export const applyRequireHooks = () => { From a766105ca18ea13def8691a2fcd1da70da0a9ad8 Mon Sep 17 00:00:00 2001 From: Rob Stanford Date: Mon, 26 Jun 2023 17:06:05 +0100 Subject: [PATCH 3/7] chore: fix eslint complaining --- packages/runtime/src/templates/requireHooks.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/runtime/src/templates/requireHooks.ts b/packages/runtime/src/templates/requireHooks.ts index 9633f57656..4359dea8cf 100644 --- a/packages/runtime/src/templates/requireHooks.ts +++ b/packages/runtime/src/templates/requireHooks.ts @@ -1,4 +1,4 @@ -/* eslint-disable n/no-extraneous-require, no-underscore-dangle, @typescript-eslint/no-explicit-any */ +/* eslint-disable no-underscore-dangle, @typescript-eslint/no-explicit-any */ // This is a modified version of the require hooks from Next.js // https://github.com/vercel/next.js/blob/b04c70573ac199a9bb3ea42201e0865e610d5b67/packages/next/src/server/require-hook.ts @@ -114,4 +114,4 @@ export const applyRequireHooks = () => { // We use `bind` here to avoid referencing outside variables to create potential memory leaks. }.bind(null, resolveFilename, requireHooks) } -/* eslint-enable n/no-extraneous-require, no-underscore-dangle, @typescript-eslint/no-explicit-any */ +/* eslint-enable no-underscore-dangle, @typescript-eslint/no-explicit-any */ From 7c23568d2a727304b72d8500a6cb1103d07d6efc Mon Sep 17 00:00:00 2001 From: Rob Stanford Date: Tue, 27 Jun 2023 17:51:47 +0100 Subject: [PATCH 4/7] fix: strip query string when matching path for prebundling react --- packages/runtime/src/templates/server.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/runtime/src/templates/server.ts b/packages/runtime/src/templates/server.ts index 577d6d7b0d..85d9c16ac5 100644 --- a/packages/runtime/src/templates/server.ts +++ b/packages/runtime/src/templates/server.ts @@ -74,7 +74,7 @@ const getNetlifyNextServer = (NextServer: NextServerType) => { const appPathsManifest = this.getAppPathsManifest?.() const routes = routesManifest && [...routesManifest.staticRoutes, ...routesManifest.dynamicRoutes] - const matchedRoute = routes?.find((route) => new RegExp(route.regex).test(path)) + const matchedRoute = routes?.find((route) => new RegExp(route.regex).test(path.split('?')[0])) const isAppRoute = appPathsManifest && matchedRoute ? appPathsManifest[joinPaths(matchedRoute.page, 'page')] : false From 3e41a0893472151cf4c1c11f0e75e1e22346ce19 Mon Sep 17 00:00:00 2001 From: Rob Stanford Date: Tue, 27 Jun 2023 17:54:51 +0100 Subject: [PATCH 5/7] chore: added comment about hook deletion --- packages/runtime/src/templates/requireHooks.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/runtime/src/templates/requireHooks.ts b/packages/runtime/src/templates/requireHooks.ts index 4359dea8cf..732115cc74 100644 --- a/packages/runtime/src/templates/requireHooks.ts +++ b/packages/runtime/src/templates/requireHooks.ts @@ -89,7 +89,7 @@ const resolveRequireHooks = () => { const resolvedPath = require.resolve(path, opts) mode.set(hook, resolvedPath) } catch { - // ignore + // module not present (older version of Next.js) mode.delete(hook) } }) From 78fc4d69b69de595abc5f39e7185478e1da5075d Mon Sep 17 00:00:00 2001 From: Rob Stanford Date: Wed, 28 Jun 2023 09:22:22 +0100 Subject: [PATCH 6/7] chore: make require hook error handling more specific --- packages/runtime/src/templates/requireHooks.ts | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/packages/runtime/src/templates/requireHooks.ts b/packages/runtime/src/templates/requireHooks.ts index 732115cc74..149033695a 100644 --- a/packages/runtime/src/templates/requireHooks.ts +++ b/packages/runtime/src/templates/requireHooks.ts @@ -88,9 +88,13 @@ const resolveRequireHooks = () => { try { const resolvedPath = require.resolve(path, opts) mode.set(hook, resolvedPath) - } catch { - // module not present (older version of Next.js) - mode.delete(hook) + } catch (error) { + if (error.code === 'MODULE_NOT_FOUND') { + // module not present (older version of Next.js) + mode.delete(hook) + } else { + throw error + } } }) }) From 17371ad2a44e3ad7380044fd2a8e188cc81c32d8 Mon Sep 17 00:00:00 2001 From: Rob Stanford Date: Thu, 29 Jun 2023 12:45:09 +0100 Subject: [PATCH 7/7] fix: swap require hook forEach orer --- packages/runtime/src/templates/requireHooks.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/runtime/src/templates/requireHooks.ts b/packages/runtime/src/templates/requireHooks.ts index 149033695a..301e9f96e2 100644 --- a/packages/runtime/src/templates/requireHooks.ts +++ b/packages/runtime/src/templates/requireHooks.ts @@ -84,7 +84,7 @@ const resolveRequireHooks = () => { // resolve require hooks with module paths requireHooks.forEach((mode) => { - mode.forEach((hook, path) => { + mode.forEach((path, hook) => { try { const resolvedPath = require.resolve(path, opts) mode.set(hook, resolvedPath)