fix: auto-save not detecting plugin block field changes#1119
Conversation
When editing plugin block attributes via the Block Kit modal, the previous code used raw editor.view.dispatch(tr) with setNodeMarkup. For atom nodes with attribute-only changes, this may not reliably trigger TipTap's onUpdate callback, which means the PortableTextEditor onChange never fires and the parent ContentEditor never sees the change — breaking auto-save dirty detection. Switch to editor.chain().command() which goes through TipTap's command pipeline and guarantees onUpdate fires, propagating the change to formData and triggering auto-save. Fixes emdash-cms#1118
🦋 Changeset detectedLatest commit: 3d78cb1 The changes in this PR will be included in the next version bump. This PR includes changesets to release 14 packages
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 |
|
All contributors have signed the CLA ✍️ ✅ |
There was a problem hiding this comment.
Pull request overview
Fixes an auto-save reliability issue in the admin Portable Text editor where edits to existing plugin block attributes (via the Block Kit modal) were not consistently detected as document updates, preventing dirty-state tracking and auto-save from triggering.
Changes:
- Switch plugin block attribute updates from
editor.view.dispatch(tr)to a TipTapeditor.chain().command(...).run()transaction path. - Ensure attribute-only updates on
pluginBlockatom nodes propagate through TipTap’s update pipeline soonChangecan fire reliably.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| // Editing an existing block — update its attributes in place. | ||
| // Use the chain API so TipTap's onUpdate fires reliably | ||
| // (raw view.dispatch may not trigger onUpdate for attribute-only | ||
| // changes on atom nodes in some TipTap versions). | ||
| editor |
|
I have read the CLA Document and I hereby sign the CLA |
|
/review |
@emdash-cms/admin
@emdash-cms/auth
@emdash-cms/blocks
@emdash-cms/cloudflare
emdash
create-emdash
@emdash-cms/gutenberg-to-portable-text
@emdash-cms/x402
@emdash-cms/plugin-ai-moderation
@emdash-cms/plugin-atproto
@emdash-cms/plugin-audit-log
@emdash-cms/plugin-color
@emdash-cms/plugin-embeds
@emdash-cms/plugin-forms
@emdash-cms/plugin-webhook-notifier
commit: |
|
Now I have a clear picture. Let me assess this: Review assessment:
The fix is small, targeted, correctly diagnosed, and uses a known-safe pattern. The main weakness is the missing regression test, already raised by Copilot. I won't pile on with a duplicate inline comment — I'll skip posting a review. LGTM! |
What does this PR do?
Fixes auto-save not detecting changes when editing plugin block fields via the Block Kit modal. When a user edits an existing block's attributes through the modal, the change was silently lost unless they also made a separate text edit.
Closes #1118
Type of change
Checklist
pnpm typecheckpassespnpm lintpassespnpm testpasses (or targeted tests for my change)pnpm formathas been runmessages.pochanges except in translation PRs — a workflow extracts catalogs on merge tomain.AI-generated code disclosure
Root Cause
When editing an existing plugin block's attributes through the Block Kit modal,
handlePluginBlockInsertinPortableTextEditor.tsxusededitor.view.dispatch(tr)withsetNodeMarkupto update the node. For atom nodes (atom: true) with attribute-only changes, this bypasses TipTap's command pipeline and does not reliably trigger theonUpdatecallback. As a result:PortableTextEditor'sonChangenever firesContentEditor'sformDatanever updatesserializeEditorState()produces the same string aslastSavedDataisDirtystaysfalseFix
Replace
editor.view.dispatch(tr)witheditor.chain().command(({ tr }) => { ... }).run(). The chain API goes through TipTap's full command pipeline, which guaranteesonUpdatefires and propagates the change throughonChange→handleFieldChange→setFormData→ auto-save dirty detection.How to test
demos/simplewith a plugin that has Block Kit fields (e.g., forms plugin)Screenshots / test output
N/A — behavioral fix, no visual change.