Skip to content

[0.42-r2 H4] morph-inserted islands render client-initial content instead of the server's DSD #579

Description

@SisyphusZheng

Severity: high · Category: implementation bug

Evidence (verified in browser). A DOMParser-parsed island node inserted via insertBefore/appendChild does NOT get its <template shadowrootmode> instantiated (DSD only applies at parse). The element upgrades via the CSR fallback: hasShadow: true but the shadow contains the client-initial render (verified: count span empty) while the server-fresh DSD content stays as an inert light-DOM template (templateConsumed: false). So a morphed-in island shows STALE initial content instead of the fresh server render, and future __islandIntact comparisons see the leftover template.

Fix. On every morph insertion (insertBefore/appendChild in __morphChildren, and the island-replace path in __morphNode), walk the inserted subtree and manually instantiate any template[shadowrootmode] whose parent has no shadowRoot (attachShadow({mode}) + append template.content, remove the template). Then upgrades hydrate the server content via the existing DSD path.

Acceptance. e2e: a response containing a NEW island instance morphs in with the server's content and is interactive.


Filed from the 0.42 round-2 review (docs/audit/2026-07-28-alpha5-round2-review.md). Target line: 0.42.0-alpha.6.

Metadata

Metadata

Assignees

No one assigned

    Labels

    0.42.0-alpha.60.42 round-2 review remediation (morph client hardening)bugSomething isn't working

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions