Composed-tree shadow DOM capture, sized invisible spacers, track re-anchoring, block fill-width slides, javascript: href sanitization
- Walker serializes the composed (flattened) tree: open shadow roots walk as host children with <slot> replaced by its assigned light nodes (or fallback), so custom-element content (product cards, web components) is captured instead of arriving childless - In-flow visibility:hidden nodes with a nonzero border box survive the prune as sized invisible placeholders - ghost spacers carry load-bearing geometry - When pruning drops leading in-flow children of a horizontally-translated track, the baked translateX is re-anchored by their aggregate margin-box width (settled carousel tracks return to origin instead of pushing real content off-screen); animation-owned transforms unaffected - Circular-shrink slide guard counts block-level fill children as width-deriving regardless of wAuto (block auto-width IS fill), pinning library-sized slide widths uniformly - javascript: hrefs emit as "#" and the link gate normalizes both sides 382 tests pass (18 new), typecheck clean. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Fable 5
parent
6e4921884c
commit
762855664c
@@ -11,6 +11,7 @@ import {
|
||||
PACKAGE_JSON_TW,
|
||||
PACKAGE_JSON_VITE,
|
||||
PACKAGE_JSON_VITE_TW,
|
||||
propsList,
|
||||
type ComponentRegistry,
|
||||
} from "../src/generate/app.js";
|
||||
import { DITTO_WIRE_TSX, ACCORDION_TSX } from "../src/generate/interactive.js";
|
||||
@@ -165,3 +166,34 @@ describe("lottie-web is declared when its import is emitted (fix 7)", () => {
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// ---- FIX 5: javascript: hrefs are sanitized to an inert '#' ----
|
||||
// React refuses to render a `javascript:*` href verbatim — it rewrites it to a long
|
||||
// `javascript:throw new Error('React has blocked a javascript: URL…')` string that no longer matches
|
||||
// the source href in the link gate. Emit an inert `#` instead (the script behaviour isn't reproduced).
|
||||
describe("javascript: hrefs are emitted as an inert '#' (FIX 5)", () => {
|
||||
const hrefOf = (n: IRNode): string | undefined => {
|
||||
const p = propsList(n, new Map(), "https://example.test/").find(([k]) => k === "href");
|
||||
return p ? JSON.parse(p[1]) : undefined;
|
||||
};
|
||||
it("rewrites a javascript: href to #", () => {
|
||||
const a = node("n1", "a", computed());
|
||||
a.attrs = { href: "Javascript:{}" };
|
||||
assert.equal(hrefOf(a), "#", "a javascript: href is sanitized to #");
|
||||
});
|
||||
it("rewrites javascript:void(0) too (case-insensitive, with args)", () => {
|
||||
const a = node("n1", "a", computed());
|
||||
a.attrs = { href: "javascript:void(0)" };
|
||||
assert.equal(hrefOf(a), "#");
|
||||
});
|
||||
it("leaves a normal in-page anchor href untouched", () => {
|
||||
const a = node("n1", "a", computed());
|
||||
a.attrs = { href: "#section" };
|
||||
assert.equal(hrefOf(a), "#section", "a real fragment link is preserved");
|
||||
});
|
||||
it("leaves an ordinary external href resolved (not collapsed to #)", () => {
|
||||
const a = node("n1", "a", computed());
|
||||
a.attrs = { href: "https://example.test/products" };
|
||||
assert.equal(hrefOf(a), "https://example.test/products");
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user