feat: let canvas extensions select a section by keepthebyte · Pull Request #1282 · adobe/da-live · GitHub
Skip to content

feat: let canvas extensions select a section - #1282

Draft
keepthebyte wants to merge 2 commits into
adobe:mainfrom
keepthebyte:selectsection-extension-action
Draft

keepthebyte wants to merge 2 commits into
adobe:mainfrom
keepthebyte:selectsection-extension-action

Conversation

@keepthebyte

Copy link
Copy Markdown

Closes #1281 — please read that first for the motivation. Opening this as a draft: it is a concrete suggestion to argue about, not a merge request. Happy for the team to take the idea and implement it their own way.

What

Adds one action to the canvas extension channel, selectSection, backed by a selectSection(view, sectionIndex) helper in editor-utils/blocks.js.

Why

A BYO panel extension can already read the document (the handshake hands it { org, repo, ref, path } and the IMS token, so it can fetch page source from admin.da.live) and insert into it (sendHTML → insertHTML). What it cannot do is move the selection, and that blocks two things:

  1. Jumping the canvas to a section. A plugin listing the page's sections cannot scroll the editor to one when clicked, the way ew-page-outline does.
  2. Editing an existing section. insertHTML does replaceRange(from, to, …), so the edit loop already works — it just needs something to put the selection on the right node first. Without that the only remaining route is writing source via admin.da.live underneath a live collab session, which we are deliberately not doing.

Selecting the whole section rather than only scrolling to it is the load-bearing choice: it delivers the jump and leaves a replaceable range under the existing sendHTML, so editing needs no second API.

Implementation notes

  • getSectionRanges reuses the same "split top-level nodes on horizontal_rule" walk that deleteSection and moveSection already use, rather than introducing a second notion of what a section is.
  • Ends in TextSelection + scrollIntoView() + view.focus(), mirroring what the outline path does.
  • Replies on the port with { action: 'selectSectionResult', details: { ok } } so a plugin can feature-detect and degrade rather than fail silently — our prototype shows an explicit "this host does not support it yet" note on timeout.
  • Nothing here lets a plugin mutate the document outside the editor. Edits still go through ProseMirror and collab.

Open questions for the team

  • Address shape. sectionIndex is what the existing block/section helpers already speak, but a prose-index or node address would be more general and would survive section reordering better. Happy to change.
  • Naming / placement. selectSection sits alongside the other verbs in iframe-protocol.js; if extension capabilities are meant to be gated or declared per plugin, this should probably go through that instead.
  • Should a read-only variant exist (scrollToSection) for plugins that want to navigate without disturbing the user's selection? We did not add one because the replaceable range is the point, but the two uses are separable.

Testing

Verified against a real customer page in a local canvas: clicking a section in a plugin panel scrolls the editor to it, and a subsequent getSelection → edit → sendHTML round-trips the section's prose HTML — preserving block content and any non-audience Style tokens, and updating only what the plugin intended.

This is driven by an authoring plugin we built for section-scoped personalization; happy to share it if that helps evaluate the shape.

Cedric Huesler and others added 2 commits August 28, 2026 12:10
A panel extension can read the document and insert into it, but has no way to
move the selection to a known place. That blocks two things a structural
authoring plugin needs: jumping the canvas to a section the way the outline
rail does, and editing a section at all -- insertHTML already replaces the
current selection, so the edit loop works as soon as something can position
that selection.

Without it the only route left is writing source via admin.da.live underneath
a live collab session, which risks clobbering or being clobbered by the y.js
document.

selectSection reuses the same "split top-level nodes on horizontal_rule" walk
that deleteSection and moveSection already use, and ends in TextSelection plus
scrollIntoView. Selecting the whole section rather than only scrolling to it
is deliberate: it gives the jump and leaves a replaceable range under
sendHTML, so editing needs no second API.

Refs adobe#1281

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01EmqV8wmTVrzTsEYCd5y5rT
Jumping and range-selecting are different asks, and only the first has
precedent. The outline addresses blocks and prose items, never sections --
its section row is a drag handle with add/delete, not a click target -- and
the jump it performs is canvasBus.editorSelectState -> _scrollDocToBlock.

Driving the view directly, as the first version did, works but goes around
all of that: the outline highlight stays stale and _broadcastSelectedNode
never runs, so the wysiwyg side never learns about the selection. scrollToBlock
now emits on the bus with the same blockIndex address instead.

selectSection stays, for a different reason than navigation: getBlockPositions
excludes NON_BLOCK_TABLE_NAMES, so a section's metadata table has no blockIndex
and cannot be addressed at all. The section range is what makes it reachable,
and leaves something for sendHTML to replace.

Refs adobe#1281

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01EmqV8wmTVrzTsEYCd5y5rT
@keepthebyte

Copy link
Copy Markdown
Author

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

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Canvas extensions cannot move the selection, which blocks structural authoring plugins

1 participant