Skip to content

Convert modal-form metadata fetches to async load/set pairs#310

Merged
namedgraph merged 6 commits into
developfrom
rf-modal-form-templates
Jun 6, 2026
Merged

Convert modal-form metadata fetches to async load/set pairs#310
namedgraph merged 6 commits into
developfrom
rf-modal-form-templates

Conversation

@namedgraph
Copy link
Copy Markdown
Member

The five modal/typeahead form rendering paths each fetched type-metadata, property-metadata, constraints, and object-metadata synchronously via document() inside their terminal render functions, blocking the UI thread on 3-4 sequential round-trips per render.

Promote each fetch to an async load/set pair invoked as steps in the existing ixsl:promise chains:

  • ldh:load-type-metadata / ldh:set-type-metadata (set-type-metadata stripped of its sync work, now just extracts response body)
  • ldh:load-constraints / ldh:set-constraints (new pair)
  • Reuse the existing ldh:load-property-metadata and ldh:load-object-metadata in client/block.xsl, extended to accept pre-computed URIs from context (backward-compatible)

Each of the five chains (btn-edit, btn-app-settings, add-constructor, typeahead-row-form, row-form-submit-violation) is extended with the new load/set steps before its terminal render function. The render functions are correspondingly stripped of sync work and now just read metadata from context.

ldh:modal-form-submit-violation was sync; converted to start a promise chain and terminate in a new ldh:render-modal-form-violation.

To uniformly identify the resource being edited across all three modal flows in the submit-violation re-render path, the Container/Item creation modal now also carries @about on its wrapper div (the new resource URL), matching btn-edit and btn-app-settings. The submit handlers read $block/@about directly without a fallback.

namedgraph and others added 6 commits June 6, 2026 00:00
The five modal/typeahead form rendering paths each fetched
type-metadata, property-metadata, constraints, and object-metadata
synchronously via document() inside their terminal render functions,
blocking the UI thread on 3-4 sequential round-trips per render.

Promote each fetch to an async load/set pair invoked as steps in the
existing ixsl:promise chains:
- ldh:load-type-metadata / ldh:set-type-metadata (set-type-metadata
  stripped of its sync work, now just extracts response body)
- ldh:load-constraints / ldh:set-constraints (new pair)
- Reuse the existing ldh:load-property-metadata and
  ldh:load-object-metadata in client/block.xsl, extended to accept
  pre-computed URIs from context (backward-compatible)

Each of the five chains (btn-edit, btn-app-settings, add-constructor,
typeahead-row-form, row-form-submit-violation) is extended with the
new load/set steps before its terminal render function. The render
functions are correspondingly stripped of sync work and now just
read metadata from context.

ldh:modal-form-submit-violation was sync; converted to start a
promise chain and terminate in a new ldh:render-modal-form-violation.

To uniformly identify the resource being edited across all three
modal flows in the submit-violation re-render path, the Container/Item
creation modal now also carries @about on its wrapper div (the new
resource URL), matching btn-edit and btn-app-settings. The submit
handlers read $block/@about directly without a fallback.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Two small follow-ups to the modal-form refactor so the
Container/Item creation modal renders identically before and after a
constraint-violation re-render:

- subject-slug onkeyup handler now also keeps the modal-constructor
  div's @about attribute in sync with the new URI (alongside the
  existing 'su' input value and form @action sync), so the submit
  handler's $block/@about discriminator stays correct after the user
  edits the slug.

- bs2:FormControl slug-style template (imports/default.xsl) now matches
  Container/Item resources by either @Rdf:nodeID (initial SPIN
  construction: blank node) or @Rdf:about (violation response: carries
  the submitted URI). The same body works for both because $action
  carries the resource URL in either case; without this the violation
  re-render fell through to the generic full-URI control.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The async load/set pair conversion in 3ba3dc6 made each metadata
fetch a self-contained step but left them threaded sequentially.
Independent fetches (shapes, constructors, type-metadata,
property-metadata, constraints, object-metadata) read disjoint context
keys, so they can fan out via ixsl:all and converge through a single
merge step. New helper ldh:fire-load-set-parallel#2 in functions.xsl
encapsulates the pattern; new ldh:reset-cursor#0 + ixsl:finally replace
duplicated end-of-chain cursor cleanup.

Refactored sites:
- form.xsl:1415 (typeahead-row-form): 21 hops -> 5, two parallel
  batches around set-typeahead-form-resource as SHACL+SPIN merge barrier
- modal.xsl:820 (add-constructor):    18 hops -> 5
- modal.xsl:1103 (app-settings):      21 hops -> 6, type-metadata pair
  uses an identity load-fn to preserve the GET request already baked
  by load-edited-resource

Wall-clock per flow: ~4-6 sequential round-trips -> ~2.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Mirrors the modal-form refactor from 2443668 across the remaining
form chains: btn-edit row-form, row-form constraint-violation re-render,
and the two parallel modal chains (btn-edit + btn-app-settings, and
modal-form violation re-render). The serial then-chain is replaced with
ldh:fire-load-set-parallel over the load/request/response/set tuples;
cursor reset moves into ixsl:finally so it runs on both success and
failure paths.

Adds ldh:fetch-and-load-edited-resource as the shared seed for chains
whose first hop is the edited-resource GET; downstream parallel pairs
pass an identity load-fn for type-metadata because the seed already
baked the GET-style type-metadata-request into context.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The template removed @name='ol'/'ou'/'ob' from inputs whose value was
empty at submit time, but it mutated the live DOM. When a submit failed
constraint validation and the form was re-rendered, the @name attributes
stayed stripped; a follow-up submit with newly filled values silently
dropped those inputs because parse-rdf-post filters by @name. Net effect:
after any first-submit validation error, the next submit produced an
empty <rdf:RDF/> request, the server accepted it, and the row-form
success handler crashed in $new-block (required exactly-one, got zero).

ldh:parse-rdf-post already filters empty non-'su' values inline via
$value-inputs[@name = 'su' or not(ixsl:get(., 'value') = '')], so this
template was redundant on top of being destructive.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The admin subdomain link in the user dropdown opens in a new tab; tag it
with class="external" so it picks up the same affordance (icon, styling)
as other external links.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@namedgraph namedgraph merged commit 197ab9c into develop Jun 6, 2026
1 check passed
@namedgraph namedgraph deleted the rf-modal-form-templates branch June 6, 2026 14:48
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.

1 participant