Skip to content

fix(compiler-core): parenthesise v-for key in v-memo cache guard - #15724

Open
luc122c wants to merge 1 commit into
vuejs:mainfrom
luc122c:fix/compiler-v-memo-key-parens
Open

luc122c wants to merge 1 commit into
vuejs:mainfrom
luc122c:fix/compiler-v-memo-key-parens

Conversation

@luc122c

@luc122c luc122c commented Sep 30, 2026 •

Copy link
Copy Markdown
Contributor

Closes #15723.

The v-memo + v-for cache guard inlined the :key expression without parentheses, so a ternary key parsed as cond ? a : b && _isMemoSame(...) and _isMemoSame(undefined, _memo) was called on the first render. Wraps the key expression in parentheses and covers it with a test.

Summary by CodeRabbit

  • Bug Fixes
    • Fixed v-memo cache reuse for v-for items with conditional keys, ensuring the key comparison is evaluated correctly.

@coderabbitai

coderabbitai Bot commented Sep 30, 2026 •

Copy link
Copy Markdown

Review in Change Stack →

Navigate logical layers of code changes, visualize relationships, and explore their blast radius.

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Advanced

Run ID: b6eb1d06-1d94-468b-bdc6-c334e7bfd8ab

📥 Commits

Reviewing files that changed from the base of the PR and between 4ab865a and 2bbeecc.

⛔ Files ignored due to path filters (1)
  • packages/compiler-core/__tests__/transforms/__snapshots__/vMemo.spec.ts.snap is excluded by !**/*.snap
📒 Files selected for processing (2)
  • packages/compiler-core/__tests__/transforms/vMemo.spec.ts
  • packages/compiler-core/src/transforms/vFor.ts

Included review availability: This review used your included allowance. Your plan provides up to 10 included reviews per hour; 9 remain after this review.


📝 Walkthrough

Walkthrough

The compiler now wraps keyed v-for expressions in parentheses when it generates the v-memo cache guard. A compiler test checks the generated guard with a conditional key expression.

Changes

v-memo key guard

Layer / File(s) Summary
Parenthesize the key in the memo guard
packages/compiler-core/src/transforms/vFor.ts, packages/compiler-core/__tests__/transforms/vMemo.spec.ts
The generated cache guard now parenthesizes the key expression. A compiler test checks the generated comparison for a conditional key.

Priority: ➖ Normal

Estimated code review effort: 2 (Simple) | ~10 minutes

Change: Bug fix · Severity of issue fixed: Medium

Suggested reviewers: edison1105

Merge Risk: ⚪ Minimal · up to 2bbee

No actionable merge-blocking risk remains in the reviewed change.

Architecture Summary

Architecture risk: 🔵 Low · up to 2bbee

The change affects 1 system.

Changed systems: packages/compiler-core

Architecture concerns
No architecture-level concerns identified.

Review details

Systems and components

  • observed — packages/compiler-core (library) was modified; 2 changed files map to changed impact.

Before / after behavior

  • observed — Modified behavior in packages/compiler-core/tests/transforms/vMemo.spec.ts: Added a test compiling a v-for element with the conditional key x ? x : y and memo dependencies [x, y === z]; it asserts that generated code compares _cached.key with the conditional key expression.
  • observed — Modified behavior in packages/compiler-core/src/transforms/vFor.ts: The memo cache condition now parenthesizes keyExp on the right side of the _cached.key equality check; the prior generated comparison emitted keyExp without parentheses.
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Linked Issues check ⚠️ Warning The compiler change in packages/compiler-core/src/transforms/vFor.ts parenthesizes the :key expression and addresses the precedence defect in issue #15723. The added compiler test checks generated… Add a runtime regression test for v-memo with v-for and a ternary :key. Verify first-render mounting and SSR rendering without an exception.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly and concisely describes the main change: parenthesizing the v-for key in the v-memo cache guard.
Out of Scope Changes check ✅ Passed The whole pull request changes only the v-memo and v-for compiler guard and adds a focused compiler test. Both changes directly support issue #15723. No unrelated change is shown.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check. Docstring coverage is scoped to functions touched by this diff. Analyzed 0 functions across 2…
Full details: Linked Issues check

Explanation

The compiler change in packages/compiler-core/src/transforms/vFor.ts parenthesizes the :key expression and addresses the precedence defect in issue #15723. The added compiler test checks generated code for a ternary key. The issue also requires the component to render without a first-render exception, including under SSR, and identifies a runtime regression test as coverage. The PR summary reports no runtime or SSR test, so that behavior is not verified by an automated test.

  • Fix all pre-merge checks with AI
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create a new PR

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@pkg-pr-new

pkg-pr-new Bot commented Sep 30, 2026

Copy link
Copy Markdown

Open in StackBlitz

@vue/compiler-core

pnpm add https://pkg.pr.new/@vue/compiler-core@15724
npm i https://pkg.pr.new/@vue/compiler-core@15724
yarn add https://pkg.pr.new/@vue/compiler-core@15724.tgz

@vue/compiler-dom

pnpm add https://pkg.pr.new/@vue/compiler-dom@15724
npm i https://pkg.pr.new/@vue/compiler-dom@15724
yarn add https://pkg.pr.new/@vue/compiler-dom@15724.tgz

@vue/compiler-sfc

pnpm add https://pkg.pr.new/@vue/compiler-sfc@15724
npm i https://pkg.pr.new/@vue/compiler-sfc@15724
yarn add https://pkg.pr.new/@vue/compiler-sfc@15724.tgz

@vue/compiler-ssr

pnpm add https://pkg.pr.new/@vue/compiler-ssr@15724
npm i https://pkg.pr.new/@vue/compiler-ssr@15724
yarn add https://pkg.pr.new/@vue/compiler-ssr@15724.tgz

@vue/reactivity

pnpm add https://pkg.pr.new/@vue/reactivity@15724
npm i https://pkg.pr.new/@vue/reactivity@15724
yarn add https://pkg.pr.new/@vue/reactivity@15724.tgz

@vue/runtime-core

pnpm add https://pkg.pr.new/@vue/runtime-core@15724
npm i https://pkg.pr.new/@vue/runtime-core@15724
yarn add https://pkg.pr.new/@vue/runtime-core@15724.tgz

@vue/runtime-dom

pnpm add https://pkg.pr.new/@vue/runtime-dom@15724
npm i https://pkg.pr.new/@vue/runtime-dom@15724
yarn add https://pkg.pr.new/@vue/runtime-dom@15724.tgz

@vue/server-renderer

pnpm add https://pkg.pr.new/@vue/server-renderer@15724
npm i https://pkg.pr.new/@vue/server-renderer@15724
yarn add https://pkg.pr.new/@vue/server-renderer@15724.tgz

@vue/shared

pnpm add https://pkg.pr.new/@vue/shared@15724
npm i https://pkg.pr.new/@vue/shared@15724
yarn add https://pkg.pr.new/@vue/shared@15724.tgz

vue

pnpm add https://pkg.pr.new/vue@15724
npm i https://pkg.pr.new/vue@15724
yarn add https://pkg.pr.new/vue@15724.tgz

@vue/compat

pnpm add https://pkg.pr.new/@vue/compat@15724
npm i https://pkg.pr.new/@vue/compat@15724
yarn add https://pkg.pr.new/@vue/compat@15724.tgz

commit: 2bbeecc

@github-actions

Copy link
Copy Markdown

Size Report

Bundles

File Size Gzip Brotli
runtime-dom.global.prod.js 109 kB 41.3 kB 37 kB
vue.global.prod.js 168 kB 61.5 kB 54.6 kB

Usages

Name Size Gzip Brotli
createApp (CAPI only) 50.8 kB 19.6 kB 18 kB
createApp 58.9 kB 22.7 kB 20.8 kB
createSSRApp 63.7 kB 24.7 kB 22.5 kB
defineCustomElement 65.2 kB 24.6 kB 22.5 kB
overall 73.5 kB 28 kB 25.5 kB

@edison1105 edison1105 added ready to merge The PR is ready to be merged. scope: compiler 🔨 p3-minor-bug Priority 3: this fixes a bug, but is an edge case that only affects very specific usage. labels Sep 30, 2026

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

🔨 p3-minor-bug Priority 3: this fixes a bug, but is an edge case that only affects very specific usage. ready to merge The PR is ready to be merged. scope: compiler

Projects

None yet

Development

Successfully merging this pull request may close these issues.

compiler-core: v-memo + v-for cache guard is not parenthesised, so a ternary :key crashes at render

2 participants