fix(core): guard CONSUMED_PARAMS against non-extensible params#13042
Merged
satya164 merged 4 commits intoreact-navigation:mainfrom Mar 19, 2026
Merged
fix(core): guard CONSUMED_PARAMS against non-extensible params#13042satya164 merged 4 commits intoreact-navigation:mainfrom
satya164 merged 4 commits intoreact-navigation:mainfrom
Conversation
When using React Compiler or other tools that freeze objects, `route.params` can become non-extensible. The `Object.defineProperty` call to set `CONSUMED_PARAMS` then throws: `TypeError: Cannot add new property 'CONSUMED_PARAMS'` Add an `Object.isExtensible()` check before attempting to define the property, matching the pattern suggested in react-navigation#13033. Fixes react-navigation#13033
|
Hey @gtokman! Thanks for opening your first pull request in this repo. If you haven't already, make sure to read our contribution guidelines. |
✅ Deploy Preview for react-navigation-example ready!
To edit notification comments on pull requests, go to your Netlify project configuration. |
|
Hey @autofix-ci[bot]! Thanks for opening your first pull request in this repo. If you haven't already, make sure to read our contribution guidelines. |
✅ Deploy Preview for react-navigation-example ready!
To edit notification comments on pull requests, go to your Netlify project configuration. |
…ARAMS Replace the symbol-based mutation approach with a module-level WeakSet to track consumed params. This avoids mutating route.params entirely, which fixes compatibility with React Compiler and other tools that freeze objects. The WeakSet approach: - Does not mutate route.params (works with frozen/sealed objects) - Automatically cleans up when params objects are GC'd (no memory leaks) - Preserves the same semantics: params are marked as consumed after being processed by a nested navigator
b786210 to
37df7d3
Compare
…tracking Instead of a global WeakSet, store consumed params state per navigator instance using a React context provided by SceneView. - Add ConsumedParamsContext with WeakRef<object> | null state - SceneView provides the context, scoping tracking to each navigator - useNavigationBuilder consumes the context to check/set consumed params - No mutation of route.params (works with frozen objects / React Compiler) - No shared state between navigator instances Fixes react-navigation#13033
37df7d3 to
9fcfa2e
Compare
satya164
pushed a commit
that referenced
this pull request
Mar 19, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Object.isExtensible()check before theObject.defineProperty(route.params, CONSUMED_PARAMS, ...)call inuseNavigationBuilderroute.paramsnon-extensible, the current code throwsTypeError: Cannot add new property 'CONSUMED_PARAMS'Related