From e6f2cc54744786941b4c3e41f0317371d5e0f289 Mon Sep 17 00:00:00 2001 From: Houssein Djirdeh Date: Tue, 17 May 2022 17:18:54 -0400 Subject: [PATCH 1/2] fixes Script function child check in document --- packages/next/pages/_document.tsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/next/pages/_document.tsx b/packages/next/pages/_document.tsx index badc0f7a6b85c..1c5ba47e93bf7 100644 --- a/packages/next/pages/_document.tsx +++ b/packages/next/pages/_document.tsx @@ -12,7 +12,7 @@ import type { import { BuildManifest, getPageFiles } from '../server/get-page-files' import { cleanAmpPath } from '../server/utils' import { htmlEscapeJsonString } from '../server/htmlescape' -import Script, { ScriptProps } from '../client/script' +import { ScriptProps } from '../client/script' import isError from '../lib/is-error' import { HtmlContext } from '../shared/lib/html-context' @@ -605,7 +605,7 @@ export class Head extends Component< const filteredChildren: ReactNode[] = [] React.Children.forEach(children, (child: any) => { - if (child.type === Script) { + if (typeof child.type === 'function' && child.type.name === 'Script') { if (child.props.strategy === 'beforeInteractive') { scriptLoader.beforeInteractive = ( scriptLoader.beforeInteractive || [] From cc57ed96e5d9c1a9f071ef960e35f9f33a5fa74e Mon Sep 17 00:00:00 2001 From: Houssein Djirdeh Date: Wed, 18 May 2022 12:21:42 -0400 Subject: [PATCH 2/2] updates per review comments --- packages/next/build/webpack-config.ts | 2 +- packages/next/pages/_document.tsx | 4 +- .../index.test.ts | 63 +++++++++++++++++++ 3 files changed, 66 insertions(+), 3 deletions(-) rename test/e2e/{next-script-worker-strategy => next-script}/index.test.ts (85%) diff --git a/packages/next/build/webpack-config.ts b/packages/next/build/webpack-config.ts index eb2c76523fe69..597dbe9bcfd01 100644 --- a/packages/next/build/webpack-config.ts +++ b/packages/next/build/webpack-config.ts @@ -816,7 +816,7 @@ export default async function getBaseWebpackConfig( } const notExternalModules = - /^(?:private-next-pages\/|next\/(?:dist\/pages\/|(?:app|document|link|image|constants|dynamic)$)|string-hash$)/ + /^(?:private-next-pages\/|next\/(?:dist\/pages\/|(?:app|document|link|image|constants|dynamic|script)$)|string-hash$)/ if (notExternalModules.test(request)) { return } diff --git a/packages/next/pages/_document.tsx b/packages/next/pages/_document.tsx index 1c5ba47e93bf7..badc0f7a6b85c 100644 --- a/packages/next/pages/_document.tsx +++ b/packages/next/pages/_document.tsx @@ -12,7 +12,7 @@ import type { import { BuildManifest, getPageFiles } from '../server/get-page-files' import { cleanAmpPath } from '../server/utils' import { htmlEscapeJsonString } from '../server/htmlescape' -import { ScriptProps } from '../client/script' +import Script, { ScriptProps } from '../client/script' import isError from '../lib/is-error' import { HtmlContext } from '../shared/lib/html-context' @@ -605,7 +605,7 @@ export class Head extends Component< const filteredChildren: ReactNode[] = [] React.Children.forEach(children, (child: any) => { - if (typeof child.type === 'function' && child.type.name === 'Script') { + if (child.type === Script) { if (child.props.strategy === 'beforeInteractive') { scriptLoader.beforeInteractive = ( scriptLoader.beforeInteractive || [] diff --git a/test/e2e/next-script-worker-strategy/index.test.ts b/test/e2e/next-script/index.test.ts similarity index 85% rename from test/e2e/next-script-worker-strategy/index.test.ts rename to test/e2e/next-script/index.test.ts index ebbfbac28b374..6e37026d104e4 100644 --- a/test/e2e/next-script-worker-strategy/index.test.ts +++ b/test/e2e/next-script/index.test.ts @@ -4,6 +4,69 @@ import { NextInstance } from 'test/lib/next-modes/base' import { BrowserInterface } from 'test/lib/browsers/base' import { waitFor } from 'next-test-utils' +describe('beforeInteractive', () => { + let next: NextInstance + + beforeAll(async () => { + next = await createNext({ + files: { + 'pages/_document.js': ` + import { Html, Head, Main, NextScript } from 'next/document' + import Script from 'next/script' + + export default function Document() { + return ( + + + + + +
+ + + + ) + } + `, + 'pages/index.js': ` + import Script from 'next/script' + + export default function Home() { + return ( + <> +

Home page

+ + ) + } + `, + }, + dependencies: { + react: '17.0.2', + 'react-dom': '17.0.2', + }, + }) + }) + afterAll(() => next.destroy()) + + it('Script is injected server-side', async () => { + let browser: BrowserInterface + + try { + browser = await webdriver(next.url, '/') + + const script = await browser.eval( + `document.querySelector('script[data-nscript="beforeInteractive"]')` + ) + expect(script).not.toBeNull() + } finally { + if (browser) await browser.close() + } + }) +}) + describe('experimental.nextScriptWorkers: false with no Partytown dependency', () => { let next: NextInstance