Skip to content

Commit f72c707

Browse files
committed
chore: warn when running tests against stale build
1 parent 40a4c11 commit f72c707

File tree

5 files changed

+79
-0
lines changed

5 files changed

+79
-0
lines changed

jest.config.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ const createJestConfig = nextJest()
77
const customJestConfig = {
88
displayName: process.env.IS_WEBPACK_TEST ? 'webpack' : 'Turbopack',
99
testMatch: ['**/*.test.js', '**/*.test.ts', '**/*.test.jsx', '**/*.test.tsx'],
10+
globalSetup: '<rootDir>/jest-global-setup.ts',
1011
setupFilesAfterEnv: ['<rootDir>/jest-setup-after-env.ts'],
1112
verbose: true,
1213
rootDir: 'test',

packages/next/taskfile.js

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2684,6 +2684,16 @@ export async function build(task, opts) {
26842684
['precompile', 'compile', 'check_error_codes', 'generate_types'],
26852685
opts
26862686
)
2687+
// Write git commit hash to dist for stale build detection during tests
2688+
try {
2689+
const { stdout: commitHash } = await execa('git', ['rev-parse', 'HEAD'])
2690+
await fs.writeFile(
2691+
join(__dirname, 'dist', '.build-commit'),
2692+
commitHash.trim()
2693+
)
2694+
} catch (err) {
2695+
// Ignore errors (e.g., not in a git repo)
2696+
}
26872697
}
26882698

26892699
export async function generate_types(task, opts) {

run-tests.js

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ const glob = promisify(_glob)
1313
const exec = promisify(execOrig)
1414
const core = require('@actions/core')
1515
const { getTestFilter } = require('./test/get-test-filter')
16+
const { checkBuildFreshness } = require('./test/lib/check-build-freshness')
1617

1718
// Do not rename or format. sync-react script relies on this line.
1819
// prettier-ignore
@@ -219,6 +220,9 @@ async function main() {
219220
// Ensure we have the arguments awaited from yargs.
220221
argv = await argv
221222

223+
// Check for stale or missing build
224+
await checkBuildFreshness()
225+
222226
// `.github/workflows/build_reusable.yml` sets this, we should use it unless
223227
// it's overridden by an explicit `--concurrency` argument.
224228
const envConcurrency =

test/jest-global-setup.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
import { checkBuildFreshness } from './lib/check-build-freshness'
2+
3+
export default async function globalSetup() {
4+
await checkBuildFreshness()
5+
}

test/lib/check-build-freshness.js

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
const { existsSync } = require('fs')
2+
const fsp = require('fs/promises')
3+
const path = require('path')
4+
const { execSync } = require('child_process')
5+
6+
const YELLOW = '\x1b[33m'
7+
const RESET = '\x1b[0m'
8+
9+
/**
10+
* Check if the Next.js build is fresh (matches current git HEAD).
11+
* Prints warnings to console if build is missing or stale.
12+
* @returns {Promise<void>}
13+
*/
14+
async function checkBuildFreshness() {
15+
const distPath = path.join(__dirname, '../../packages/next/dist')
16+
const buildCommitPath = path.join(distPath, '.build-commit')
17+
18+
if (!existsSync(distPath)) {
19+
console.warn(`${YELLOW}⚠️ WARNING: No build found!${RESET}`)
20+
console.warn(
21+
`${YELLOW} The packages/next/dist directory does not exist.${RESET}`
22+
)
23+
console.warn(
24+
`${YELLOW} Run \`pnpm build\` before running tests.\n${RESET}`
25+
)
26+
return
27+
}
28+
29+
if (!existsSync(buildCommitPath)) {
30+
console.warn(`${YELLOW}⚠️ WARNING: Build may be stale!${RESET}`)
31+
console.warn(
32+
`${YELLOW} Unable to verify build freshness (no .build-commit marker).${RESET}`
33+
)
34+
console.warn(`${YELLOW} Run \`pnpm build\` to rebuild.\n${RESET}`)
35+
return
36+
}
37+
38+
try {
39+
const buildCommit = (await fsp.readFile(buildCommitPath, 'utf8')).trim()
40+
const currentCommit = execSync('git rev-parse HEAD', {
41+
encoding: 'utf8',
42+
}).trim()
43+
44+
if (buildCommit !== currentCommit) {
45+
console.warn(`${YELLOW}⚠️ WARNING: Build is stale!${RESET}`)
46+
console.warn(
47+
`${YELLOW} Build was compiled at commit: ${buildCommit.slice(0, 8)}${RESET}`
48+
)
49+
console.warn(
50+
`${YELLOW} Current HEAD is at commit: ${currentCommit.slice(0, 8)}${RESET}`
51+
)
52+
console.warn(`${YELLOW} Run \`pnpm build\` to rebuild.\n${RESET}`)
53+
}
54+
} catch (err) {
55+
// Ignore errors (e.g., git not available)
56+
}
57+
}
58+
59+
module.exports = { checkBuildFreshness }

0 commit comments

Comments
 (0)