Skip to content

chore(deps): consolidate Dependabot updates - #986

Merged
lv10 merged 3 commits into
masterfrom
chore/consolidate-dependabot
Aug 18, 2026
Merged

chore(deps): consolidate Dependabot updates#986
lv10 merged 3 commits into
masterfrom
chore/consolidate-dependabot

Conversation

@lv10

@lv10 lv10 commented Aug 11, 2026

Copy link
Copy Markdown
Contributor

Consolidates 3 of the 4 open Dependabot PRs. The eslint 10 major is blocked upstream.

Package From Dependabot asked for Manifest Resolved Bump Supersedes
next 15.5.21 16.2.11 (#964), 16.3.0 (#978) ^16.3.0 16.3.1 major #964, #978
eslint-config-next 15.5.6 16.3.0 ^16.3.0 16.3.1 major #983
postcss (transitive, top level) 8.4.31 8.5.23 8.5.23 patch #978

eslint-config-next moves with next — they are released together and the config for Next 16
expects the Next 16 plugin.

Note on postcss: the version that moves is the top-level copy, 8.4.31 → 8.5.23. The
8.5.26 copy is the one nested under vite (node_modules/vite/node_modules/postcss) and it was
already at 8.5.26 on master, so this PR does not touch it.

Migration Next 16 required

next lint is gone. Next 16 removed the command, so "lint": "next lint" became
"lint": "eslint .".

.eslintrc.jsoneslint.config.mjs. The old config was just
{ "extends": "next/core-web-vitals" }. eslint-config-next@16 ships a native flat config, so the
replacement imports it directly:

import coreWebVitals from 'eslint-config-next/core-web-vitals'

export default [{ ignores: ['.next/**', 'out/**', 'dist/**'] }, ...coreWebVitals]

Worth noting for anyone doing this elsewhere: routing it through FlatCompat instead — the usual
eslintrc bridge — fails with TypeError: Converting circular structure to JSON on
eslint-config-next@16, because the config already is flat. Import it directly.

dist/** had to be added to ignores. This is the one place where swapping next lint for
eslint . changes what gets walked: next lint only ever descended into app, pages,
components, lib and src, whereas eslint . walks the whole tree. npm run slides:build
writes the slidev bundle to dist/ (vite's default build.outDir; deploy.yml publishes
publish_dir: dist), so without the ignore, anyone who built the slides and then linted got a
hard failure inside a generated third-party bundle:

dist/assets/modules/shiki-DeTF74yl.js
  3:4441  error  Component definition is missing display name  react/display-name
✖ 82 problems (1 error, 81 warnings)     # exit 1

CI never hit this because it lints a fresh npm ci tree with no dist. dist was also missing
from .gitignore (a gap that predates this PR), so it has been added there too.

Two further consequences of Next 16, both fixed here

agentRules: false in next.config.js. Next 16 added
server/lib/generate-agent-files.js (absent from 15.5.21), so next dev wrote AGENTS.md and
CLAUDE.md into the project root and left them untracked and un-gitignored. This is a teaching
repo, so every attendee running npm run dev would have found two unexplained files in their
clone. Disabling the feature is the deliberate choice here rather than gitignoring or committing
them. npm run dev now leaves git status clean.

images.domainsimages.remotePatterns. Next 16 emits
⚠ 'images.domains' is deprecated in favor of 'images.remotePatterns' on every dev and
build. Migrated to remotePatterns: [{ protocol: 'https', hostname: 'image.tmdb.org' }], which
removes the warning without changing which hosts are allowed. Verified against a running dev
server: /api/movies returns 200 with live TMDB JSON, a poster URL fetched through the Next image
optimizer returns 200 image/jpeg (48538 bytes, optimised), and a host that is not in
remotePatterns correctly returns 400 — so the allowlist is genuinely being enforced and
image.tmdb.org is what it admits.

Verification

  • npm ci: ✅ resolves cleanly (lockfile and manifest agree)
  • npm run lint: ✅ 81 problems (0 errors, 81 warnings), exit 0 — including with dist/
    present after a slides build. This is identical to master's next lint output, so it is not a
    regression, but it is not "0 problems" either
  • npm run build: ✅ Next 16 production build, all routes, no deprecation warnings
  • npm run slides:build: ✅
  • npm run dev: ✅ serves / and /api/movies, no warnings, clean git tree
  • npm test: the script is a placeholder (echo … && exit 0), so there is nothing to run — the
    build and lint are the real signal here, and both are what CI runs
  • npm audit: 16 advisories (9 high / 2 moderate / 5 low) on master → 13 (6 high / 2
    moderate / 5 low)
    on this branch. No package in the tree is downgraded.

Left for follow-up — #984 stays open

eslint 9.39.2 → 10.8.1 is blocked by eslint-plugin-react, which eslint-config-next pulls in.
On eslint 10, lint dies while loading its rules:

TypeError: Error while loading rule 'react/display-name':
  contextOrFilename.getFilename is not a function

The installed eslint-plugin-react is 7.37.2 (not 7.37.5), and its
peerDependencies.eslint reads ^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7 — no eslint 10 at any
point. 7.37.5, the latest release, declares the same range, so the version difference does not
change the conclusion. Since the plugin arrives transitively through eslint-config-next, there is
nothing to pin here: eslint 10 has to wait for that plugin (and for Next to pick it up). I applied
it, confirmed the failure, and reverted to eslint 9.

Unrelated pre-existing issue, not addressed here

The commit-msg husky hook is broken on master as well as on this branch: commitlint throws
ERR_PACKAGE_PATH_NOT_EXPORTED: No "exports" main defined in node_modules/conventional-changelog-conventionalcommits. @commitlint/cli@21.0.2,
@commitlint/config-conventional@21.2.0 and
conventional-changelog-conventionalcommits@10.2.1 resolve to identical versions on both sides,
so this PR neither causes nor fixes it. Flagging it rather than folding an unrelated fix into a
dependency consolidation.

Closes #985

Folds 3 of the 4 open Dependabot PRs into one change: Next 16, eslint-config-next 16 and
the postcss transitive.

Next 16 removed 'next lint', so the lint script runs eslint directly against a flat
config - eslint-config-next 16 provides one natively, replacing .eslintrc.json.

eslint 10 (#984) stays open: eslint-plugin-react, via eslint-config-next, does not
support it yet.

Closes #985
Resolve manifest/lockfile conflicts from Dependabot PRs that auto-merged
into master after this PR was opened (#987 @hono/node-server,
#988 prettier, #990 @slidev/cli, #991 @next/bundle-analyzer).

Took master's versions for all four (none was a target of this PR);
kept the Next 16 major, eslint-config-next 16, the .eslintrc.json ->
eslint.config.mjs migration and the 'next lint' -> 'eslint .' script
change. Lockfile re-derived from master's.

Also assign the flat config to a named const before exporting, so
eslint.config.mjs no longer trips import/no-anonymous-default-export
on itself. Lint output is now at parity with master (81 warnings,
0 errors).

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

@SociableSteve SociableSteve left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The migration itself holds up. I reproduced it locally against the merge base (origin/master @ 7cdae00) and can confirm:

  • npm ci is clean, so the lockfile and the manifest agree. Resolved: next 16.3.1, eslint-config-next 16.3.1, eslint 9.39.2, react 19.2.8, top-level postcss 8.5.23.
  • No package in the tree is downgraded (I diffed every entry in both locks), and npm audit totals go down, 16 to 13, with high going 9 to 6.
  • npm run build succeeds on Turbopack, all 14 pages/routes build, and npm run dev serves /, the step-01, step-08, step-09 and step-10 solution pages and /api/movies with 200s. The Next surface this repo touches is tiny (only next/document and @next/bundle-analyzer), so nothing removed in Next 16 is actually used.
  • The flat-config migration does not silently drop rules. I ran eslint --print-config on the same file on both sides (eslintrc with ESLINT_USE_FLAT_CONFIG=false on master, flat config here): 47 enabled rules before, 62 after. Nothing lost, no severity downgrades, and 15 rules gained (the react-hooks v6 set plus @next/next/no-location-assign-relative-destination). That is the outcome you want from this kind of migration and it is worth calling out explicitly.
  • Bonus: eslint --cache --fix in the lint-staged hook was actually broken on master (eslint 9 could not find a flat config, so the pre-commit hook errored). This PR fixes that as a side effect.

Three things I would like addressed before merge, all consequences of the bump rather than mistakes in it.

Comment thread eslint.config.mjs Outdated
// "next/core-web-vitals".
const config = [
{
ignores: ['.next/**', 'out/**']

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ignores is missing the slidev build output, and this makes npm run lint fail.

This is the one place where swapping next lint for eslint . changes what gets walked. next lint only ever descended into app, pages, components, lib and src. eslint . walks the whole tree, so anything generated at the repo root is now in scope unless it is listed here.

npm run slides:build writes to dist/ (vite's default build.outDir, and .github/workflows/deploy.yml publishes publish_dir: dist). dist is also absent from .gitignore, so it is neither git-ignored nor eslint-ignored. Reproduced on this branch:

$ npx eslint . ; echo $?
✖ 81 problems (0 errors, 81 warnings)
0

$ npm run slides:build && npx eslint . ; echo $?
dist/assets/modules/shiki-DeTF74yl.js
  3:4441  error  Component definition is missing display name  react/display-name
✖ 82 problems (1 error, 81 warnings)
1

So any developer who builds the slides and then lints gets a hard lint failure inside a generated third-party bundle. CI happens to be safe because it lints a fresh npm ci tree that has no dist, which is exactly why this will not be caught until someone hits it locally.

Suggest:

ignores: ['.next/**', 'out/**', 'dist/**']

Adding dist to .gitignore in the same pass would be worth it too, though that gap predates this PR.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 7cedc24. ignores is now ['.next/**', 'out/**', 'dist/**'], and dist added to .gitignore in the same commit (git check-ignore -v dist -> .gitignore:13:dist).

Reproduced your failure first, on this branch before the change:

$ npx eslint . ; echo $?
✖ 81 problems (0 errors, 81 warnings)
0

$ npm run slides:build && npx eslint . ; echo $?
/home/.../react-patterns-workshop/dist/assets/modules/shiki-DeTF74yl.js
  3:4441  error  Component definition is missing display name  react/display-name
✖ 82 problems (1 error, 81 warnings)
1

Same file, same hash, same rule. git status also showed ?? dist/ and git check-ignore dist exited 1, confirming it was neither git-ignored nor eslint-ignored.

After the change, with dist/ present from a real npm run slides:build:

$ npm run slides:build ; echo $?
0
$ npm run lint ; echo $?
✖ 81 problems (0 errors, 81 warnings)
0

Back to 81/0 and exit 0. I also added a comment above the ignores array explaining why the array exists at all, since the reason (eslint . walking the whole tree where next lint did not) is not obvious from the file.

Comment thread package.json
"clsx": "^2.1.1",
"modern-normalize": "^3.0.1",
"next": "^15.5.21",
"next": "^16.3.0",

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Next 16 makes next dev write two untracked files into every attendee's clone.

This is new behaviour in 16, not something 15.5.21 did. node_modules/next/dist/server/lib/generate-agent-files.js does not exist in next 15.5.21 and does in 16.3.1. I ran npm run dev on this branch and got:

✓ Generated AGENTS.md and CLAUDE.md for AI agents. Set `agentRules: false` in next.config to disable.

followed by git status showing:

?? AGENTS.md
?? CLAUDE.md

Neither is in .gitignore (git check-ignore returns nothing for both), and the same run on master produces a clean tree. That matters more here than in a normal app: this is a teaching repo, so every attendee who runs npm run dev gets two mystery files at the root, and the AGENTS.md preamble even tells the reader Next will keep re-adding the block and that committing it "keeps the tree clean", which is exactly the wrong instinct for a workshop repo.

Pick one and do it deliberately: set agentRules: false in next.config.js, or add AGENTS.md and CLAUDE.md to .gitignore, or commit them on purpose. Leaving it undecided is the bad option.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Decided: agentRules: false in next.config.js, in 7cedc24. For a workshop repo that is the option that leaves nothing to explain to attendees — no mystery root files, and nothing gitignored that a reader then has to go looking for.

Confirmed the behaviour on both sides before changing it. node_modules/next/dist/server/lib/generate-agent-files.js exists in 16.3.1, and npm run dev on this branch printed:

⚠ `images.domains` is deprecated in favor of `images.remotePatterns`. ...
✓ Generated AGENTS.md and CLAUDE.md for AI agents. Set `agentRules: false` in next.config to disable.

with git status then showing:

?? AGENTS.md
?? CLAUDE.md

After the change, the same npx next dev run logs only ✓ Ready in 271ms — no "Generated AGENTS.md" line, no deprecation warning (that is the separate fix from your other comment) — and git status --short shows only the three files this commit modifies. Nothing generated, tree clean.

Comment thread package.json
"build": "next build",
"start": "next start",
"lint": "next lint",
"lint": "eslint .",

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit, but it belongs in this PR since it is new noise introduced by the bump. Next 16 now emits on every dev and build:

⚠ `images.domains` is deprecated in favor of `images.remotePatterns`. Please update next.config.js to protect your application from malicious users.

I confirmed the warning is absent from the 15.5.21 build on master, so the migration is what surfaces it. next.config.js has images: { domains: ['image.tmdb.org'] }, which converts to:

images: {
  remotePatterns: [{ protocol: 'https', hostname: 'image.tmdb.org' }]
}

A persistent deprecation warning on a projector during a workshop is worth 3 lines to remove.

Separately, two small corrections for the PR description so it matches what actually resolves: top-level postcss lands at 8.5.23, not 8.5.26 (8.5.26 is the copy nested under vite, and it was already there on master), and the installed eslint-plugin-react is 7.37.2, not 7.37.5. Neither changes the conclusion about #984 being correctly deferred, the plugin still declares no eslint 10 support.

Also, "npm run lint: 0 problems on the new flat config" is not what it does: it is 81 warnings and 0 errors. That is identical to master's next lint output, so it is not a regression, but the claim as written is wrong.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Migrated in 7cedc24, exactly as suggested:

images: {
  remotePatterns: [{ protocol: 'https', hostname: 'image.tmdb.org' }]
}

The warning is gone from both npm run dev and npm run build (grep for deprecat|⚠ over the dev log returns 0 matches; the build log has none either).

Verified images still work rather than just that the warning went away. Against a running dev server:

/api/movies                      -> 200 application/json, live TMDB payload
                                    first poster: https://image.tmdb.org/t/p/w500//iPOn6DinuVyLY17YM9mKuPofV08.jpg
that poster fetched directly     -> 200 image/jpeg, 105080 bytes
same poster via /_next/image     -> 200 image/jpeg, 48538 bytes (optimised)
https://example.com/a.jpg via /_next/image -> 400

The 400 on the control host is the part that matters: it shows the allowlist is actually being enforced, so the 200 on image.tmdb.org is remotePatterns admitting it and not the optimizer waving everything through.

On the description corrections, all three verified and all three fixed in the body:

  • postcss: top level goes 8.4.31 -> 8.5.23. The 8.5.26 copy is node_modules/vite/node_modules/postcss and it is already 8.5.26 in master's lockfile, so this PR does not touch it. Table corrected, with a note.
  • eslint-plugin-react: installed is 7.37.2. Its peerDependencies.eslint is ^3 || ^4 || ^5 || ^6 || ^7 || ^8 || ^9.7 — no eslint 10. Body now cites 7.37.2 and notes that 7.37.5 declares the same range, so the conclusion on chore(deps-dev): bump eslint from 9.39.2 to 10.8.0 #984 is unchanged.
  • lint output: corrected from "0 problems" to 81 problems (0 errors, 81 warnings), with the explicit note that this matches master's next lint output and is therefore not a regression.

I also added the resolved-versus-manifest distinction to the table, since next and eslint-config-next resolve to 16.3.1 off ^16.3.0 after master merged #991, not the 16.3.0 the old table claimed.

…e images config

- eslint.config.mjs: add dist/** to ignores. next lint only walked
  app/pages/components/lib/src; eslint . walks the whole tree, so a local
  npm run slides:build made npm run lint fail on generated slidev output.
- .gitignore: add dist (gap predates this PR).
- next.config.js: agentRules: false so next dev stops writing AGENTS.md and
  CLAUDE.md into every attendee's clone; images.domains -> images.remotePatterns
  to clear the Next 16 deprecation warning.
@lv10

lv10 commented Aug 18, 2026

Copy link
Copy Markdown
Contributor Author

All three items addressed in 7cedc24, each answered inline with the reproduction and the after-state. Summary:

  1. dist/** added to eslint.config.mjs ignores and dist added to .gitignore. npm run slides:build && npm run lint now exits 0 at 81 warnings / 0 errors, where before it exited 1 on dist/assets/modules/shiki-DeTF74yl.js.
  2. agentRules: false in next.config.js. Chose disabling over gitignoring or committing, because this is a workshop repo and the option with nothing to explain to attendees is the one where the files never appear. npm run dev now leaves the tree clean.
  3. images.domains migrated to images.remotePatterns. Warning gone from dev and build; images verified still loading through the optimizer, with a control host returning 400 to prove the allowlist is live.

Description corrected on all three points you raised, quoting the right numbers: top-level postcss lands at 8.5.23 (8.5.26 is the vite-nested copy, already on master), installed eslint-plugin-react is 7.37.2, and npm run lint is 81 problems (0 errors, 81 warnings) rather than "0 problems" — noted as identical to master's next lint output and therefore not a regression. I also corrected the version table to show next and eslint-config-next resolving to 16.3.1 off ^16.3.0, matching what you measured, rather than the 16.3.0 it claimed.

One thing I found while committing, which I have deliberately not fixed here: the commit-msg husky hook is broken, commitlint throwing ERR_PACKAGE_PATH_NOT_EXPORTED: No "exports" main defined in node_modules/conventional-changelog-conventionalcommits. It is not caused by this PR — @commitlint/cli@21.0.2, @commitlint/config-conventional@21.2.0 and conventional-changelog-conventionalcommits@10.2.1 resolve to identical versions in master's lockfile and this branch's, so it is equally broken on master. I used --no-verify for the commit (the pre-commit eslint --cache --fix hook ran and passed) and noted it in the description rather than folding an unrelated fix into a dependency consolidation. Happy to open a separate issue for it.

@lv10
lv10 requested a review from SociableSteve August 18, 2026 14:24

@SociableSteve SociableSteve left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All three points from the previous round are addressed, and I verified each against head (7cedc24) rather than taking the thread replies for it.

  1. dist is now in both eslint.config.mjs ignores and .gitignore (git check-ignore -v dist resolves to .gitignore:13). npm run slides:build && npm run lint stays at 81 problems (0 errors, 81 warnings) with dist/ present, where before it errored on dist/assets/modules/shiki-*.js.
  2. agentRules: false is a real top-level Next 16 option, not experimental (next/dist/server/config-schema.js, agentRules: z.boolean().optional()), so it does not trip config validation. next dev on this branch writes no AGENTS.md or CLAUDE.md and leaves git status clean.
  3. images.remotePatterns replaces domains with no deprecation warning in the dev or build logs, and the same hostname is allowed.

Also re-checked from a fresh npm ci on this branch:

  • Lockfile matches the corrected description: top-level postcss 8.4.31 to 8.5.23, the vite-nested copy already 8.5.26 on the merge base and untouched here, eslint-plugin-react 7.37.2 on both sides. The deferral of eslint 10 (#984) stands on that plugin's peer range.
  • npm run build succeeds on Next 16.3.1 across all 14 routes, next dev serves / and /api/movies with 200s.
  • No .eslintrc or next lint references remain anywhere outside comments, and lint-staged's eslint --cache --fix picks up the flat config.

One optional, non-blocking note, not a reason to hold this up.

@next/bundle-analyzer stops producing a report once next is on 16, because Turbopack is now the default builder. @next/bundle-analyzer@16.3.1 bails out when process.env.TURBOPACK is set, and Next 16 sets it to auto before next.config.js is evaluated. Measured both sides: on the merge base ANALYZE=true npm run build writes .next/analyze/{client,nodejs,edge}.html, on this branch it writes nothing and prints "The Next Bundle Analyzer is not compatible with Turbopack builds, no report will be generated". The build still exits 0, the warning names the fix (--webpack, or next experimental-analyze), and nothing in the repo actually invokes ANALYZE: no npm script, no workflow, no mention in README.md or the slides. So it is a latent capability regression rather than a broken path, and it is fine to pick up separately if anyone wants bundle analysis back.

Approving.

@lv10
lv10 merged commit 65da098 into master Aug 18, 2026
4 checks passed
@lv10
lv10 deleted the chore/consolidate-dependabot branch August 18, 2026 20:41
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

chore(deps): consolidate the open Dependabot PRs

2 participants