perf(Dialog): use stable context value reference#7620
perf(Dialog): use stable context value reference#7620hectahertz wants to merge 4 commits intomainfrom
Conversation
🦋 Changeset detectedLatest commit: daee366 The changes in this PR will be included in the next version bump. This PR includes changesets to release 1 package
Not sure what this means? Click here to learn what changesets are. Click here if you're a maintainer who wants to add another changeset to this PR |
|
There was a problem hiding this comment.
Pull request overview
This PR optimizes @primer/react’s Dialog by avoiding a new DialogContext.Provider value object allocation on every render, since the context is used only as a presence sentinel.
Changes:
- Hoists the
DialogContextprovider value into a module-level constant for a stable reference. - Adds a patch changeset documenting the performance optimization.
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
| packages/react/src/Dialog/Dialog.tsx | Uses a module-level constant for DialogContext.Provider value instead of an inline {} per render. |
| .changeset/perf-dialog-stable-context.md | Patch changeset describing the stable context value optimization. |
packages/react/src/Dialog/Dialog.tsx
Outdated
|
|
||
| // useful to determine whether we're inside a Dialog from a nested component | ||
| export const DialogContext = React.createContext<object | undefined>(undefined) | ||
| const DIALOG_CONTEXT_VALUE = {} |
There was a problem hiding this comment.
DIALOG_CONTEXT_VALUE is a shared mutable object across all Dialog instances. If any consumer ever mutates the context value (even accidentally), that mutation will persist across renders and leak between dialogs. To keep the “presence check only” invariant and avoid mutation-related footguns, use an immutable sentinel (e.g. Object.freeze({}) as done in deprecated/utils/create-slots.tsx).
| const DIALOG_CONTEXT_VALUE = {} | |
| const DIALOG_CONTEXT_VALUE = Object.freeze({}) |
| --- | ||
| '@primer/react': patch | ||
| --- | ||
|
|
||
| Use stable object reference for DialogContext value to prevent unnecessary re-renders |
There was a problem hiding this comment.
PR metadata indicates tests were “Added/updated”, but this PR only changes the Dialog context value and adds a changeset (no test updates). Please either update the checklist/description to reflect reality, or add coverage that would fail if the context value regressed to an unstable reference.
Closes #
DialogContext.Providerwas receivingvalue={{}}which creates a new object reference on every render. Since this context is only used as a presence check (useContext(DialogContext) !== undefined), a module-level constant works perfectly.Changelog
New
N/A
Changed
DialogContextvalue to a module-level constant to avoid new object allocation on every renderRemoved
N/A
Rollout strategy
Testing & Reviewing
Trivial change, no behavioral difference. The context value is only used as a presence check.
Merge checklist