diff --git a/tests/e2e/simple-app.test.ts b/tests/e2e/simple-app.test.ts index 980ad84dd0..23455ba567 100644 --- a/tests/e2e/simple-app.test.ts +++ b/tests/e2e/simple-app.test.ts @@ -12,8 +12,8 @@ test('Renders the Home page correctly', async ({ page, simple }) => { await expect(page).toHaveTitle('Simple Next App') - expect(headers['cache-status']).toMatch(/^"Next.js"; hit$/m) - expect(headers['cache-status']).toMatch(/^"Netlify Edge"; fwd=miss$/m) + expect(headers['cache-status'].replaceAll(', ', '\n')).toMatch(/^"Next.js"; hit$/m) + expect(headers['cache-status'].replaceAll(', ', '\n')).toMatch(/^"Netlify Edge"; fwd=miss$/m) // "Netlify Durable" assertion is skipped because we are asserting index page and there are possible that something else is making similar request to it // and as a result we can see many possible statuses for it: `fwd=miss`, `fwd=miss; stored`, `hit; ttl=` so there is no point in asserting on that // "Netlify Edge" status suffers from similar issue, but is less likely to manifest (only if those requests would be handled by same CDN node) and retries diff --git a/tools/build.js b/tools/build.js index 301304f5de..c622a26d67 100644 --- a/tools/build.js +++ b/tools/build.js @@ -1,6 +1,7 @@ import { createWriteStream } from 'node:fs' -import { cp, rm } from 'node:fs/promises' -import { join, resolve } from 'node:path' +import { cp, readFile, rm } from 'node:fs/promises' +import { dirname, join, resolve } from 'node:path' +import { fileURLToPath } from 'node:url' import { Readable } from 'stream' import { finished } from 'stream/promises' @@ -11,6 +12,8 @@ import glob from 'fast-glob' const OUT_DIR = 'dist' await rm(OUT_DIR, { force: true, recursive: true }) +const repoDirectory = dirname(resolve(fileURLToPath(import.meta.url), '..')) + const entryPointsESM = await glob('src/**/*.ts', { ignore: ['**/*.test.ts'] }) const entryPointsCJS = await glob('src/**/*.cts') @@ -39,7 +42,7 @@ async function bundle(entryPoints, format, watch) { name: 'mark-runtime-modules-as-external', setup(pluginBuild) { pluginBuild.onResolve({ filter: /^\..*\.c?js$/ }, (args) => { - if (args.importer.includes(join('opennextjs-netlify', 'src'))) { + if (args.importer.includes(join(repoDirectory, 'src'))) { return { path: args.path, external: true } } }) @@ -126,8 +129,38 @@ await Promise.all([ cp('src/build/templates', join(OUT_DIR, 'build/templates'), { recursive: true, force: true }), ]) +async function ensureNoRegionalBlobsModuleDuplicates() { + const REGIONAL_BLOB_STORE_CONTENT_TO_FIND = 'fetchBeforeNextPatchedIt' + + const filesToTest = await glob(`${OUT_DIR}/**/*.{js,cjs}`) + const unexpectedModulesContainingFetchBeforeNextPatchedIt = [] + let foundInExpectedModule = false + for (const fileToTest of filesToTest) { + const content = await readFile(fileToTest, 'utf-8') + if (content.includes(REGIONAL_BLOB_STORE_CONTENT_TO_FIND)) { + if (fileToTest.endsWith('run/regional-blob-store.cjs')) { + foundInExpectedModule = true + } else { + unexpectedModulesContainingFetchBeforeNextPatchedIt.push(fileToTest) + } + } + } + if (!foundInExpectedModule) { + throw new Error( + 'Expected to find "fetchBeforeNextPatchedIt" variable in "run/regional-blob-store.cjs", but it was not found. This might indicate a setup change that requires the bundling validation in "tools/build.js" to be adjusted.', + ) + } + if (unexpectedModulesContainingFetchBeforeNextPatchedIt.length !== 0) { + throw new Error( + `Bundling produced unexpected duplicates of "regional-blob-store" module in following built modules:\n${unexpectedModulesContainingFetchBeforeNextPatchedIt.map((filePath) => ` - ${filePath}`).join('\n')}`, + ) + } +} + if (watch) { console.log('Starting compilation in watch mode...') } else { + await ensureNoRegionalBlobsModuleDuplicates() + console.log('Finished building 🎉') }