Catch rejected onUpdate promises: revert + surface error instead of leaking unhandled rejection#314
Merged
Merged
Conversation
Copilot
AI
changed the title
[WIP] Fix silent loss of edits on update promise rejection
Catch rejected onUpdate promises: revert + surface error instead of leaking unhandled rejection
Jun 3, 2026
Bundle size impact
|
| Format | Base raw | PR raw | Δ raw | Base gzip | PR gzip | Δ gzip |
|---|---|---|---|---|---|---|
| esm | 54.78 KB | 54.89 KB | 🔺 +119 B (+0.21%) | 19.00 KB | 19.03 KB | 🔺 +32 B (+0.16%) |
| cjs | 56.26 KB | 56.37 KB | 🔺 +119 B (+0.21%) | 19.03 KB | 19.05 KB | 🔺 +28 B (+0.14%) |
Measured from build/index.{cjs,esm}.js. Gzip at level 9.
CarlosNZ
requested changes
Jun 3, 2026
Comment on lines
+248
to
+254
| const errorKey = | ||
| input.event === 'add' | ||
| ? 'ERROR_ADD' | ||
| : input.event === 'delete' | ||
| ? 'ERROR_DELETE' | ||
| : 'ERROR_UPDATE' | ||
| return translateRef.current(errorKey, rootNodeDataRef.current) |
Owner
There was a problem hiding this comment.
Please use the new ERROR_MESSAGE_KEY to correctly map error output strings
Contributor
Author
There was a problem hiding this comment.
Done — replaced the inline ternary with ERROR_MESSAGE_KEY[input.event] so the rejection fallback now covers rename/move too (ERROR_RENAME/ERROR_MOVE) instead of collapsing them to ERROR_UPDATE.
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.
A throwing async
onUpdateescapedhandleEditas an unhandled rejection: the edit was silently lost, edit mode closed as if it succeeded, no error UI rendered, and on newer Node/Jest the rejection terminated the process.Changes
src/JsonEditor.tsx—handleEdit: wrapawait onUpdateRef.current(input)intry/catch. On rejection, surfaceerr.message(or a bare-string throw) verbatim through the existing error slug, falling back to the event-specific default (ERROR_ADD/ERROR_DELETE/ERROR_UPDATE) — same fallback as theresult === falsebranch.setDataon rejection — deliberately matching the existing reject contract (see the comment above thefalsebranch): a slow async rejection must not clobber a newer commit that landed while it was in flight. Display revert is already driven by the node consuming the returned error string, identical to the async-falsepath.test/JsonEditor.test.tsx: promote the#271test.todoto a real test — throwsnew Error('boom'), assertssetDatais not called, original value still rendered,'boom'visible in the DOM, and nounhandledRejectionfires (regression guard against removing the try/catch).Behaviour matrix (rejection only — other branches unchanged)
throw new Error(m)mthrow 'str''str'throw(no message)