Files
Janka UrygaandGitHub 73d4493c0b test: fix next-after-app-static (#94195)
This test has been flaking in weird ways, but i also noticed that it's a
bit broken
- we were running build twice, because `next.start()` does that. this
affected what was in the logs that we assert on
- The assertion on the route was incorrect (it checked for `[page]
/static/route` instead of `[route] /static/route`, which would never be
emitted)
- ...which was hiding the fact that actually the thing *was* getting
logged due to a bug unrelated to after()

The idea in the test was essentially to assert that no after()s run at
runtime if the page/route is statically prerendered (which implicitly
also asserts that `after` itself does not make it dynamic). But it
appears that returning a `new Response()` from a static handler is
unsupported (bug imho) because it logs `Failed to update prerender cache
for /static/route Error: LRUCache: calculateSize returned 0, but size
must be > 0. Items with size 0 would never be evicted, causing unbounded
cache growth.`. As a workaround, i just gave it a non-empty body

I don't know if this will fix the flakes we've been seeing in CI. Those,
bizarrely, fail here
```
Error: can not run export while server is running, use next.stop() first
    at NextStartInstance.build (/__w/next.js/next.js/test/lib/next-modes/next-start.ts:255:13)
    at Object.build (/__w/next.js/next.js/test/e2e/app-dir/next-after-app-static/build-time/build-time.test.ts:36:36)
 ```
 https://github.com/vercel/next.js/blob/1bc1da711cd0699b620716b204b480485274ff05/test/e2e/app-dir/next-after-app-static/build-time/build-time.test.ts#L36
 
 We do `skipStart` in `nextTestSetup`, and there's no other tests running, so i have no idea what "running server" that error is referring to
2026-05-28 13:59:17 +00:00

81 lines
2.2 KiB
TypeScript

/* eslint-env jest */
import { isNextDev, nextTestSetup } from 'e2e-utils'
import * as Log from './utils/log'
import { setTimeout } from 'timers/promises'
// This test relies on next.build() so it can't work in dev mode.
const _describe = isNextDev ? describe.skip : describe
_describe('after() in static pages', () => {
const { next, skipped } = nextTestSetup({
files: __dirname,
skipDeployment: true, // reading CLI logs to observe after
skipStart: true,
})
if (skipped) return
let currentCliOutputIndex = 0
beforeEach(() => {
currentCliOutputIndex = next.cliOutput.length
})
const getLogs = () => {
if (next.cliOutput.length < currentCliOutputIndex) {
// cliOutput shrank since we started the test, so something (like a `sandbox`) reset the logs
currentCliOutputIndex = 0
}
return next.cliOutput.slice(currentCliOutputIndex)
}
const resetLogs = () => {
currentCliOutputIndex = next.cliOutput.length
}
it('runs after during build', async () => {
const buildResult = await next.build()
expect(buildResult?.exitCode).toBe(0)
{
// after should run at build time
const logsFromAfter = Log.readCliLogs(getLogs())
expect(logsFromAfter).toContainEqual({
source: '[page] /static/dynamic-error',
})
expect(logsFromAfter).toContainEqual({
source: '[page] /static/dynamic-force-static',
})
expect(logsFromAfter).toContainEqual({
source: '[route] /static/route',
})
}
resetLogs()
await next.start({ skipBuild: true })
{
const res = await next.fetch('/static/dynamic-error')
expect(res.status).toBe(200)
}
{
const res = await next.fetch('/static/dynamic-force-static')
expect(res.status).toBe(200)
}
{
const res = await next.fetch('/static/route')
expect(res.status).toBe(200)
}
await setTimeout(1000) // no other good way to make sure any possible afters ran
{
// all the pages/routes have been statically prerendered, so
// we should not observe any after()s at runtime
const logsFromAfter = Log.readCliLogs(getLogs())
expect(logsFromAfter).toHaveLength(0)
}
})
})