@barefootjs/client 0.31.7 → 0.31.9
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/csr-adapter.js +28 -0
- package/dist/runtime/component.d.ts +72 -8
- package/dist/runtime/component.d.ts.map +1 -1
- package/dist/runtime/index.d.ts +1 -1
- package/dist/runtime/index.d.ts.map +1 -1
- package/dist/runtime/index.js +35 -2
- package/dist/runtime/standalone.js +35 -2
- package/package.json +2 -2
- package/src/runtime/component.ts +104 -10
- package/src/runtime/index.ts +8 -0
package/dist/csr-adapter.js
CHANGED
|
@@ -169911,6 +169911,34 @@ var SVG_ROOT_TAGS = new Set([
|
|
|
169911
169911
|
"animateTransform",
|
|
169912
169912
|
"animateMotion"
|
|
169913
169913
|
]);
|
|
169914
|
+
var MATHML_ROOT_TAGS = new Set([
|
|
169915
|
+
"math",
|
|
169916
|
+
"mrow",
|
|
169917
|
+
"mfrac",
|
|
169918
|
+
"msup",
|
|
169919
|
+
"msub",
|
|
169920
|
+
"msubsup",
|
|
169921
|
+
"mn",
|
|
169922
|
+
"mi",
|
|
169923
|
+
"mo",
|
|
169924
|
+
"mtext",
|
|
169925
|
+
"munder",
|
|
169926
|
+
"mover",
|
|
169927
|
+
"munderover",
|
|
169928
|
+
"mtable",
|
|
169929
|
+
"mtr",
|
|
169930
|
+
"mtd",
|
|
169931
|
+
"msqrt",
|
|
169932
|
+
"mroot",
|
|
169933
|
+
"mstyle",
|
|
169934
|
+
"merror",
|
|
169935
|
+
"mpadded",
|
|
169936
|
+
"mphantom",
|
|
169937
|
+
"menclose",
|
|
169938
|
+
"semantics",
|
|
169939
|
+
"annotation",
|
|
169940
|
+
"annotation-xml"
|
|
169941
|
+
]);
|
|
169914
169942
|
|
|
169915
169943
|
// ../jsx/src/ir-to-client-js/collect-elements.ts
|
|
169916
169944
|
var EMPTY_RENDER_EXPRS = new Set(["null", "undefined", "false", "''", '""', "``"]);
|
|
@@ -141,6 +141,60 @@ export declare function escapeAttr(value: unknown): string;
|
|
|
141
141
|
* the reactive path.
|
|
142
142
|
*/
|
|
143
143
|
export declare function escapeText(value: unknown): string;
|
|
144
|
+
/**
|
|
145
|
+
* Brand carried by `bfMarkup()` — see that function's docstring. A string
|
|
146
|
+
* key (not a `Symbol`) because the brand must survive `structuredClone`
|
|
147
|
+
* (props cloned across an SSR seed / island-serialization boundary): a
|
|
148
|
+
* symbol-keyed property is silently dropped by the structured-clone
|
|
149
|
+
* algorithm, which would un-brand the value in transit.
|
|
150
|
+
*/
|
|
151
|
+
declare const BF_MARKUP_BRAND = "__bfMarkup";
|
|
152
|
+
/**
|
|
153
|
+
* Shape produced by `bfMarkup()` (#2651). Compiler-emitted code only —
|
|
154
|
+
* never construct one by hand from userland; doing so is exactly as unsafe
|
|
155
|
+
* as writing raw `innerHTML` yourself, since `escapeTextOrMarkup` /
|
|
156
|
+
* `escapeTextOrNode` (below) trust `__bfMarkup`'s contents to already be
|
|
157
|
+
* safe-to-splice HTML and skip escaping it.
|
|
158
|
+
*/
|
|
159
|
+
export interface BfMarkup {
|
|
160
|
+
readonly [BF_MARKUP_BRAND]: string;
|
|
161
|
+
}
|
|
162
|
+
/**
|
|
163
|
+
* Brand a compiler-built HTML string as pre-escaped markup safe to splice
|
|
164
|
+
* raw into a template (#2651). The compiler emits this ONLY around HTML it
|
|
165
|
+
* itself assembled from a JSX element passed at a non-`children` component
|
|
166
|
+
* prop position (`header={<strong>Title</strong>}`) — every text segment
|
|
167
|
+
* inside that assembly was already escaped node-by-node during the
|
|
168
|
+
* assembly (the same `escapeHtml` / `escapeTextSlotExpr` calls
|
|
169
|
+
* `html-template.ts` uses for ordinary element children), so the
|
|
170
|
+
* concatenated result is exactly as safe as any other compiler-emitted
|
|
171
|
+
* template fragment.
|
|
172
|
+
*
|
|
173
|
+
* Not exported from the public `@barefootjs/client` surface: this is
|
|
174
|
+
* compiler-emitted-code only, exported solely from
|
|
175
|
+
* `@barefootjs/client/runtime`. Calling it directly from userland to wrap
|
|
176
|
+
* an arbitrary string is exactly as unsafe as assigning that string to
|
|
177
|
+
* `innerHTML` yourself — the value is trusted verbatim by every consumer
|
|
178
|
+
* below.
|
|
179
|
+
*/
|
|
180
|
+
export declare function bfMarkup(html: string): BfMarkup;
|
|
181
|
+
/** Type guard for the `bfMarkup()` brand (#2651). Compiler-emitted code only — see `bfMarkup`'s docstring. */
|
|
182
|
+
export declare function isBfMarkup(value: unknown): value is BfMarkup;
|
|
183
|
+
/**
|
|
184
|
+
* `escapeText`'s counterpart for a claim-plan slot the compiler has
|
|
185
|
+
* classified `kind: 'markup'` at STATIC/initial-render time
|
|
186
|
+
* (`html-template.ts`'s `escapeTextSlotExpr`, gated on the same
|
|
187
|
+
* `ctx.dynamicElements` membership `emit-reactive.ts` reads to pick the
|
|
188
|
+
* writer kind for the REACTIVE side, below) — #2651. A `bfMarkup()`-branded
|
|
189
|
+
* value is compiler-built HTML the compiler already escaped piecewise
|
|
190
|
+
* while assembling it, and must reach the template raw, unescaped a second
|
|
191
|
+
* time; anything else (plain string, number, nullish) gets the ordinary
|
|
192
|
+
* `escapeText` treatment — this function is a strict superset of
|
|
193
|
+
* `escapeText`'s behaviour for every non-branded value, so switching a
|
|
194
|
+
* call site from one to the other never changes output unless the value
|
|
195
|
+
* is actually branded.
|
|
196
|
+
*/
|
|
197
|
+
export declare function escapeTextOrMarkup(value: unknown): string;
|
|
144
198
|
/**
|
|
145
199
|
* `escapeText`'s counterpart for a claimed 'markup' slot's REACTIVE write
|
|
146
200
|
* (slot unification A3 follow-up), where the value is a plain-JS expression
|
|
@@ -160,6 +214,14 @@ export declare function escapeText(value: unknown): string;
|
|
|
160
214
|
* before handing it to a 'markup' writer — NOT the preamble-region case
|
|
161
215
|
* (`stringify/loop.ts`), whose value is already-built HTML from a nested
|
|
162
216
|
* compiled render and must stay unescaped.
|
|
217
|
+
*
|
|
218
|
+
* A `bfMarkup()`-branded value (#2651) — a component prop re-read on every
|
|
219
|
+
* reactive re-run, e.g. `initChild`'s `get header() { return bfMarkup(...) }`
|
|
220
|
+
* getter — is unwrapped to its raw string for the same reason a `Node` is
|
|
221
|
+
* passed through untouched: the compiler already escaped its contents once
|
|
222
|
+
* during assembly, so re-escaping it (or, worse, `String()`-stringifying
|
|
223
|
+
* the wrapper object into `"[object Object]"`) would corrupt it. Checked
|
|
224
|
+
* before the `Node` branch since the two shapes are mutually exclusive.
|
|
163
225
|
*/
|
|
164
226
|
export declare function escapeTextOrNode(value: unknown): string | Node;
|
|
165
227
|
/**
|
|
@@ -167,14 +229,16 @@ export declare function escapeTextOrNode(value: unknown): string | Node;
|
|
|
167
229
|
* attribute values. All code that sets innerHTML on dynamic HTML should
|
|
168
230
|
* use this instead of raw innerHTML assignment.
|
|
169
231
|
*
|
|
170
|
-
* When `parent` is provided and lives in the SVG namespace, the
|
|
171
|
-
* is parsed under
|
|
172
|
-
* `<svg>...</svg>`; the wrapper's children are
|
|
173
|
-
* fragment so callers see the same shape as the
|
|
174
|
-
* this, dynamically-inserted SVG elements (e.g.,
|
|
175
|
-
* conditional drag preview
|
|
176
|
-
*
|
|
177
|
-
* Graph/DAG Editor block
|
|
232
|
+
* When `parent` is provided and lives in the SVG or MathML namespace, the
|
|
233
|
+
* markup is parsed under the matching foreign-content context by wrapping
|
|
234
|
+
* it in `<svg>...</svg>` / `<math>...</math>`; the wrapper's children are
|
|
235
|
+
* moved into the returned fragment so callers see the same shape as the
|
|
236
|
+
* HTML path. Without this, dynamically-inserted SVG/MathML elements (e.g.,
|
|
237
|
+
* a `<path>` in a conditional drag preview, or an `<mrow>` in a dynamic
|
|
238
|
+
* equation) end up as `HTMLUnknownElement` in the xhtml namespace and the
|
|
239
|
+
* SVG/MathML renderer ignores them. Surfaced by the Graph/DAG Editor block
|
|
240
|
+
* (#135); ported to MathML in #1096.
|
|
178
241
|
*/
|
|
179
242
|
export declare function parseHTML(html: string, parent?: Element | null): DocumentFragment;
|
|
243
|
+
export {};
|
|
180
244
|
//# sourceMappingURL=component.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"component.d.ts","sourceRoot":"","sources":["../../src/runtime/component.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AASH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AAS9C,wBAAgB,gBAAgB,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,CAExD;AAED;;;;;;GAMG;AACH,MAAM,MAAM,aAAa,GAAG;IAAE,SAAS,EAAE,IAAI,CAAC;IAAC,MAAM,EAAE,IAAI,GAAG,IAAI,CAAC;IAAC,OAAO,CAAC,EAAE,OAAO,GAAG,IAAI,CAAA;CAAE,CAAA;AAsB9F,wBAAgB,gBAAgB,CAAC,CAAC,EAAE,aAAa,GAAG,IAAI,GAAG,aAAa,GAAG,IAAI,CAI9E;AAQD;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,YAAY,CAAC,EAAE,EAAE,OAAO,GAAG,OAAO,CAQjD;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH;;;GAGG;AACH;;;;;GAKG;AACH,MAAM,WAAW,uBAAuB;IACtC,iDAAiD;IACjD,MAAM,EAAE,MAAM,CAAA;IACd,uDAAuD;IACvD,KAAK,EAAE,MAAM,CAAA;CACd;AAED,wBAAgB,eAAe,CAC7B,SAAS,EAAE,MAAM,GAAG,YAAY,EAChC,KAAK,GAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAM,EACnC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,EACrB,IAAI,CAAC,EAAE,uBAAuB,EAC9B,OAAO,CAAC,EAAE,OAAO,GAAG,IAAI,GACvB,WAAW,CAcb;AA4OD;;;;;;;;;;;;GAYG;AACH,wBAAgB,WAAW,CACzB,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC9B,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,EACrB,UAAU,CAAC,EAAE,MAAM,GAClB,MAAM,CA6ER;AA+DD;;;;;GAKG;AACH;;;;;GAKG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAEjD;AAED;;;;;;;;GAQG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAOjD;AAED;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAGjD;AAED
|
|
1
|
+
{"version":3,"file":"component.d.ts","sourceRoot":"","sources":["../../src/runtime/component.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AASH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AAS9C,wBAAgB,gBAAgB,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,CAExD;AAED;;;;;;GAMG;AACH,MAAM,MAAM,aAAa,GAAG;IAAE,SAAS,EAAE,IAAI,CAAC;IAAC,MAAM,EAAE,IAAI,GAAG,IAAI,CAAC;IAAC,OAAO,CAAC,EAAE,OAAO,GAAG,IAAI,CAAA;CAAE,CAAA;AAsB9F,wBAAgB,gBAAgB,CAAC,CAAC,EAAE,aAAa,GAAG,IAAI,GAAG,aAAa,GAAG,IAAI,CAI9E;AAQD;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,YAAY,CAAC,EAAE,EAAE,OAAO,GAAG,OAAO,CAQjD;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH;;;GAGG;AACH;;;;;GAKG;AACH,MAAM,WAAW,uBAAuB;IACtC,iDAAiD;IACjD,MAAM,EAAE,MAAM,CAAA;IACd,uDAAuD;IACvD,KAAK,EAAE,MAAM,CAAA;CACd;AAED,wBAAgB,eAAe,CAC7B,SAAS,EAAE,MAAM,GAAG,YAAY,EAChC,KAAK,GAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAM,EACnC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,EACrB,IAAI,CAAC,EAAE,uBAAuB,EAC9B,OAAO,CAAC,EAAE,OAAO,GAAG,IAAI,GACvB,WAAW,CAcb;AA4OD;;;;;;;;;;;;GAYG;AACH,wBAAgB,WAAW,CACzB,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC9B,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,EACrB,UAAU,CAAC,EAAE,MAAM,GAClB,MAAM,CA6ER;AA+DD;;;;;GAKG;AACH;;;;;GAKG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAEjD;AAED;;;;;;;;GAQG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAOjD;AAED;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAGjD;AAED;;;;;;GAMG;AACH,QAAA,MAAM,eAAe,eAAe,CAAA;AAEpC;;;;;;GAMG;AACH,MAAM,WAAW,QAAQ;IACvB,QAAQ,CAAC,CAAC,eAAe,CAAC,EAAE,MAAM,CAAA;CACnC;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,QAAQ,CAE/C;AAED,8GAA8G;AAC9G,wBAAgB,UAAU,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,QAAQ,CAU5D;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,CAGzD;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,GAAG,IAAI,CAI9D;AAaD;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,OAAO,GAAG,IAAI,GAAG,gBAAgB,CAejF"}
|
package/dist/runtime/index.d.ts
CHANGED
|
@@ -15,7 +15,7 @@ export { mapArrayLazy, type LazyRowEntry, type LazyRowPlan } from './map-array-l
|
|
|
15
15
|
export { patchLeaf } from './patch-leaf.ts';
|
|
16
16
|
export { claimSlots, lazySlots, lazyClaimSlots, textOrNode, type SlotSpec, type ClaimPlan, type ClaimedSlots, type ClaimedSlotsRW, type SlotWriter } from './claim-slots.ts';
|
|
17
17
|
export { registerTemplate, getTemplate, hasTemplate, type TemplateFn } from './template.ts';
|
|
18
|
-
export { createComponent, mountRowRoot, renderChild, parseHTML, escapeAttr, escapeText, escapeTextOrNode, } from './component.ts';
|
|
18
|
+
export { createComponent, mountRowRoot, renderChild, parseHTML, escapeAttr, escapeText, escapeTextOrNode, bfMarkup, isBfMarkup, escapeTextOrMarkup, type BfMarkup, } from './component.ts';
|
|
19
19
|
export { applyRestAttrs } from './apply-rest-attrs.ts';
|
|
20
20
|
export { spreadAttrs } from './spread-attrs.ts';
|
|
21
21
|
export { styleToCss } from './style.ts';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/runtime/index.ts"],"names":[],"mappings":"AAUA,OAAO,EACL,YAAY,EACZ,YAAY,EACZ,sBAAsB,EACtB,UAAU,EACV,cAAc,EACd,UAAU,EACV,SAAS,EACT,OAAO,EACP,OAAO,EACP,KAAK,EACL,eAAe,EACf,SAAS,EACT,OAAO,EACP,gBAAgB,EAOhB,kBAAkB,EAClB,KAAK,gBAAgB,EACrB,sBAAsB,EACtB,KAAK,QAAQ,EACb,KAAK,MAAM,EACX,KAAK,IAAI,EACT,KAAK,SAAS,EACd,KAAK,QAAQ,EACb,KAAK,iBAAiB,EACtB,KAAK,cAAc,GACpB,MAAM,6BAA6B,CAAA;AAEpC,OAAO,EACL,mBAAmB,EACnB,KAAK,aAAa,EAClB,KAAK,iBAAiB,EACtB,KAAK,aAAa,GACnB,MAAM,uBAAuB,CAAA;AAE9B,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAA;AAC9C,OAAO,EAAE,MAAM,EAAE,KAAK,UAAU,EAAE,MAAM,YAAY,CAAA;AACpD,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAA;AAClD,OAAO,EAAE,MAAM,EAAE,MAAM,cAAc,CAAA;AACrC,OAAO,EAAE,SAAS,EAAE,KAAK,WAAW,EAAE,KAAK,eAAe,EAAE,MAAM,kBAAkB,CAAA;AACpF,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAA;AAI9C,OAAO,EACL,aAAa,EACb,UAAU,EACV,cAAc,EACd,eAAe,EACf,KAAK,OAAO,GACb,MAAM,cAAc,CAAA;AAGrB,OAAO,EACL,YAAY,EACZ,WAAW,EACX,eAAe,EACf,wBAAwB,EACxB,KAAK,MAAM,EACX,KAAK,aAAa,EAClB,KAAK,UAAU,EACf,KAAK,cAAc,GACpB,MAAM,aAAa,CAAA;AAIpB,OAAO,EAAE,eAAe,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAA;AACjE,OAAO,EAAE,OAAO,EAAE,eAAe,EAAE,MAAM,eAAe,CAAA;AACxD,OAAO,EAAE,QAAQ,EAAE,gBAAgB,EAAE,MAAM,gBAAgB,CAAA;AAI3D,OAAO,EAAE,YAAY,EAAE,KAAK,YAAY,EAAE,KAAK,WAAW,EAAE,MAAM,qBAAqB,CAAA;AACvF,OAAO,EAAE,SAAS,EAAE,MAAM,iBAAiB,CAAA;AAK3C,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,cAAc,EAAE,UAAU,EAAE,KAAK,QAAQ,EAAE,KAAK,SAAS,EAAE,KAAK,YAAY,EAAE,KAAK,cAAc,EAAE,KAAK,UAAU,EAAE,MAAM,kBAAkB,CAAA;AAG5K,OAAO,EAAE,gBAAgB,EAAE,WAAW,EAAE,WAAW,EAAE,KAAK,UAAU,EAAE,MAAM,eAAe,CAAA;AAG3F,OAAO,EACL,eAAe,EACf,YAAY,EACZ,WAAW,EACX,SAAS,EACT,UAAU,EACV,UAAU,EACV,gBAAgB,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/runtime/index.ts"],"names":[],"mappings":"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"}
|
package/dist/runtime/index.js
CHANGED
|
@@ -1543,17 +1543,47 @@ function escapeText(value) {
|
|
|
1543
1543
|
return "";
|
|
1544
1544
|
return escapeAttr(value);
|
|
1545
1545
|
}
|
|
1546
|
+
var BF_MARKUP_BRAND = "__bfMarkup";
|
|
1547
|
+
function bfMarkup(html) {
|
|
1548
|
+
return { [BF_MARKUP_BRAND]: html };
|
|
1549
|
+
}
|
|
1550
|
+
function isBfMarkup(value) {
|
|
1551
|
+
if (typeof value !== "object" || value === null)
|
|
1552
|
+
return false;
|
|
1553
|
+
const proto = Object.getPrototypeOf(value);
|
|
1554
|
+
if (proto !== Object.prototype && proto !== null)
|
|
1555
|
+
return false;
|
|
1556
|
+
return typeof value[BF_MARKUP_BRAND] === "string";
|
|
1557
|
+
}
|
|
1558
|
+
function escapeTextOrMarkup(value) {
|
|
1559
|
+
if (isBfMarkup(value))
|
|
1560
|
+
return value[BF_MARKUP_BRAND];
|
|
1561
|
+
return escapeText(value);
|
|
1562
|
+
}
|
|
1546
1563
|
function escapeTextOrNode(value) {
|
|
1564
|
+
if (isBfMarkup(value))
|
|
1565
|
+
return value[BF_MARKUP_BRAND];
|
|
1547
1566
|
if (typeof Node !== "undefined" && value instanceof Node)
|
|
1548
1567
|
return value;
|
|
1549
1568
|
return escapeText(value);
|
|
1550
1569
|
}
|
|
1551
1570
|
var SVG_NS = "http://www.w3.org/2000/svg";
|
|
1571
|
+
var MATHML_NS = "http://www.w3.org/1998/Math/MathML";
|
|
1572
|
+
function namespaceWrapTagFor(parent) {
|
|
1573
|
+
if (!parent)
|
|
1574
|
+
return null;
|
|
1575
|
+
if (parent.namespaceURI === SVG_NS)
|
|
1576
|
+
return "svg";
|
|
1577
|
+
if (parent.namespaceURI === MATHML_NS)
|
|
1578
|
+
return "math";
|
|
1579
|
+
return null;
|
|
1580
|
+
}
|
|
1552
1581
|
function parseHTML(html, parent) {
|
|
1553
1582
|
const tpl = document.createElement("template");
|
|
1554
1583
|
const escaped = escapeAttrGt(html);
|
|
1555
|
-
|
|
1556
|
-
|
|
1584
|
+
const wrapTag = namespaceWrapTagFor(parent);
|
|
1585
|
+
if (wrapTag) {
|
|
1586
|
+
tpl.innerHTML = `<${wrapTag}>${escaped}</${wrapTag}>`;
|
|
1557
1587
|
const wrapper = tpl.content.firstElementChild;
|
|
1558
1588
|
const frag = document.createDocumentFragment();
|
|
1559
1589
|
if (wrapper) {
|
|
@@ -3273,6 +3303,7 @@ export {
|
|
|
3273
3303
|
lazySlots,
|
|
3274
3304
|
lazyClaimSlots,
|
|
3275
3305
|
isSSRPortal,
|
|
3306
|
+
isBfMarkup,
|
|
3276
3307
|
insert,
|
|
3277
3308
|
initChild,
|
|
3278
3309
|
hydratedScopes,
|
|
@@ -3290,6 +3321,7 @@ export {
|
|
|
3290
3321
|
findScope,
|
|
3291
3322
|
find,
|
|
3292
3323
|
escapeTextOrNode,
|
|
3324
|
+
escapeTextOrMarkup,
|
|
3293
3325
|
escapeText,
|
|
3294
3326
|
escapeAttr,
|
|
3295
3327
|
endTurn,
|
|
@@ -3309,6 +3341,7 @@ export {
|
|
|
3309
3341
|
createComponent,
|
|
3310
3342
|
cleanupPortalPlaceholder,
|
|
3311
3343
|
claimSlots,
|
|
3344
|
+
bfMarkup,
|
|
3312
3345
|
beginTurn,
|
|
3313
3346
|
batch,
|
|
3314
3347
|
applyRestAttrs,
|
|
@@ -1949,17 +1949,47 @@ function escapeText(value) {
|
|
|
1949
1949
|
return "";
|
|
1950
1950
|
return escapeAttr(value);
|
|
1951
1951
|
}
|
|
1952
|
+
var BF_MARKUP_BRAND = "__bfMarkup";
|
|
1953
|
+
function bfMarkup(html) {
|
|
1954
|
+
return { [BF_MARKUP_BRAND]: html };
|
|
1955
|
+
}
|
|
1956
|
+
function isBfMarkup(value) {
|
|
1957
|
+
if (typeof value !== "object" || value === null)
|
|
1958
|
+
return false;
|
|
1959
|
+
const proto = Object.getPrototypeOf(value);
|
|
1960
|
+
if (proto !== Object.prototype && proto !== null)
|
|
1961
|
+
return false;
|
|
1962
|
+
return typeof value[BF_MARKUP_BRAND] === "string";
|
|
1963
|
+
}
|
|
1964
|
+
function escapeTextOrMarkup(value) {
|
|
1965
|
+
if (isBfMarkup(value))
|
|
1966
|
+
return value[BF_MARKUP_BRAND];
|
|
1967
|
+
return escapeText(value);
|
|
1968
|
+
}
|
|
1952
1969
|
function escapeTextOrNode(value) {
|
|
1970
|
+
if (isBfMarkup(value))
|
|
1971
|
+
return value[BF_MARKUP_BRAND];
|
|
1953
1972
|
if (typeof Node !== "undefined" && value instanceof Node)
|
|
1954
1973
|
return value;
|
|
1955
1974
|
return escapeText(value);
|
|
1956
1975
|
}
|
|
1957
1976
|
var SVG_NS = "http://www.w3.org/2000/svg";
|
|
1977
|
+
var MATHML_NS = "http://www.w3.org/1998/Math/MathML";
|
|
1978
|
+
function namespaceWrapTagFor(parent) {
|
|
1979
|
+
if (!parent)
|
|
1980
|
+
return null;
|
|
1981
|
+
if (parent.namespaceURI === SVG_NS)
|
|
1982
|
+
return "svg";
|
|
1983
|
+
if (parent.namespaceURI === MATHML_NS)
|
|
1984
|
+
return "math";
|
|
1985
|
+
return null;
|
|
1986
|
+
}
|
|
1958
1987
|
function parseHTML(html, parent) {
|
|
1959
1988
|
const tpl = document.createElement("template");
|
|
1960
1989
|
const escaped = escapeAttrGt(html);
|
|
1961
|
-
|
|
1962
|
-
|
|
1990
|
+
const wrapTag = namespaceWrapTagFor(parent);
|
|
1991
|
+
if (wrapTag) {
|
|
1992
|
+
tpl.innerHTML = `<${wrapTag}>${escaped}</${wrapTag}>`;
|
|
1963
1993
|
const wrapper = tpl.content.firstElementChild;
|
|
1964
1994
|
const frag = document.createDocumentFragment();
|
|
1965
1995
|
if (wrapper) {
|
|
@@ -3672,6 +3702,7 @@ export {
|
|
|
3672
3702
|
lazySlots,
|
|
3673
3703
|
lazyClaimSlots,
|
|
3674
3704
|
isSSRPortal,
|
|
3705
|
+
isBfMarkup,
|
|
3675
3706
|
insert,
|
|
3676
3707
|
initChild,
|
|
3677
3708
|
hydratedScopes,
|
|
@@ -3689,6 +3720,7 @@ export {
|
|
|
3689
3720
|
findScope,
|
|
3690
3721
|
find,
|
|
3691
3722
|
escapeTextOrNode,
|
|
3723
|
+
escapeTextOrMarkup,
|
|
3692
3724
|
escapeText,
|
|
3693
3725
|
escapeAttr,
|
|
3694
3726
|
endTurn,
|
|
@@ -3708,6 +3740,7 @@ export {
|
|
|
3708
3740
|
createComponent,
|
|
3709
3741
|
cleanupPortalPlaceholder,
|
|
3710
3742
|
claimSlots,
|
|
3743
|
+
bfMarkup,
|
|
3711
3744
|
beginTurn,
|
|
3712
3745
|
batch,
|
|
3713
3746
|
applyRestAttrs,
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@barefootjs/client",
|
|
3
|
-
"version": "0.31.
|
|
3
|
+
"version": "0.31.9",
|
|
4
4
|
"description": "BarefootJS client package: reactive primitives (SSR-safe) plus browser runtime under the `/runtime` subpath (compiler target)",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -55,7 +55,7 @@
|
|
|
55
55
|
"directory": "packages/client"
|
|
56
56
|
},
|
|
57
57
|
"dependencies": {
|
|
58
|
-
"@barefootjs/shared": "0.31.
|
|
58
|
+
"@barefootjs/shared": "0.31.9"
|
|
59
59
|
},
|
|
60
60
|
"peerDependencies": {
|
|
61
61
|
"@barefootjs/jsx": ">=0.2.0"
|
package/src/runtime/component.ts
CHANGED
|
@@ -612,6 +612,80 @@ export function escapeText(value: unknown): string {
|
|
|
612
612
|
return escapeAttr(value)
|
|
613
613
|
}
|
|
614
614
|
|
|
615
|
+
/**
|
|
616
|
+
* Brand carried by `bfMarkup()` — see that function's docstring. A string
|
|
617
|
+
* key (not a `Symbol`) because the brand must survive `structuredClone`
|
|
618
|
+
* (props cloned across an SSR seed / island-serialization boundary): a
|
|
619
|
+
* symbol-keyed property is silently dropped by the structured-clone
|
|
620
|
+
* algorithm, which would un-brand the value in transit.
|
|
621
|
+
*/
|
|
622
|
+
const BF_MARKUP_BRAND = '__bfMarkup'
|
|
623
|
+
|
|
624
|
+
/**
|
|
625
|
+
* Shape produced by `bfMarkup()` (#2651). Compiler-emitted code only —
|
|
626
|
+
* never construct one by hand from userland; doing so is exactly as unsafe
|
|
627
|
+
* as writing raw `innerHTML` yourself, since `escapeTextOrMarkup` /
|
|
628
|
+
* `escapeTextOrNode` (below) trust `__bfMarkup`'s contents to already be
|
|
629
|
+
* safe-to-splice HTML and skip escaping it.
|
|
630
|
+
*/
|
|
631
|
+
export interface BfMarkup {
|
|
632
|
+
readonly [BF_MARKUP_BRAND]: string
|
|
633
|
+
}
|
|
634
|
+
|
|
635
|
+
/**
|
|
636
|
+
* Brand a compiler-built HTML string as pre-escaped markup safe to splice
|
|
637
|
+
* raw into a template (#2651). The compiler emits this ONLY around HTML it
|
|
638
|
+
* itself assembled from a JSX element passed at a non-`children` component
|
|
639
|
+
* prop position (`header={<strong>Title</strong>}`) — every text segment
|
|
640
|
+
* inside that assembly was already escaped node-by-node during the
|
|
641
|
+
* assembly (the same `escapeHtml` / `escapeTextSlotExpr` calls
|
|
642
|
+
* `html-template.ts` uses for ordinary element children), so the
|
|
643
|
+
* concatenated result is exactly as safe as any other compiler-emitted
|
|
644
|
+
* template fragment.
|
|
645
|
+
*
|
|
646
|
+
* Not exported from the public `@barefootjs/client` surface: this is
|
|
647
|
+
* compiler-emitted-code only, exported solely from
|
|
648
|
+
* `@barefootjs/client/runtime`. Calling it directly from userland to wrap
|
|
649
|
+
* an arbitrary string is exactly as unsafe as assigning that string to
|
|
650
|
+
* `innerHTML` yourself — the value is trusted verbatim by every consumer
|
|
651
|
+
* below.
|
|
652
|
+
*/
|
|
653
|
+
export function bfMarkup(html: string): BfMarkup {
|
|
654
|
+
return { [BF_MARKUP_BRAND]: html }
|
|
655
|
+
}
|
|
656
|
+
|
|
657
|
+
/** Type guard for the `bfMarkup()` brand (#2651). Compiler-emitted code only — see `bfMarkup`'s docstring. */
|
|
658
|
+
export function isBfMarkup(value: unknown): value is BfMarkup {
|
|
659
|
+
if (typeof value !== 'object' || value === null) return false
|
|
660
|
+
// Plain carrier objects only (Copilot review on #2651's PR): without the
|
|
661
|
+
// prototype check, a DOM Node (or any host object) carrying a string
|
|
662
|
+
// `__bfMarkup` expando would satisfy the shape test and be unwrapped as
|
|
663
|
+
// raw HTML — the brand must stay mutually exclusive with the Node branch
|
|
664
|
+
// of `escapeTextOrNode` by construction, not by property-name luck.
|
|
665
|
+
const proto = Object.getPrototypeOf(value)
|
|
666
|
+
if (proto !== Object.prototype && proto !== null) return false
|
|
667
|
+
return typeof (value as Record<string, unknown>)[BF_MARKUP_BRAND] === 'string'
|
|
668
|
+
}
|
|
669
|
+
|
|
670
|
+
/**
|
|
671
|
+
* `escapeText`'s counterpart for a claim-plan slot the compiler has
|
|
672
|
+
* classified `kind: 'markup'` at STATIC/initial-render time
|
|
673
|
+
* (`html-template.ts`'s `escapeTextSlotExpr`, gated on the same
|
|
674
|
+
* `ctx.dynamicElements` membership `emit-reactive.ts` reads to pick the
|
|
675
|
+
* writer kind for the REACTIVE side, below) — #2651. A `bfMarkup()`-branded
|
|
676
|
+
* value is compiler-built HTML the compiler already escaped piecewise
|
|
677
|
+
* while assembling it, and must reach the template raw, unescaped a second
|
|
678
|
+
* time; anything else (plain string, number, nullish) gets the ordinary
|
|
679
|
+
* `escapeText` treatment — this function is a strict superset of
|
|
680
|
+
* `escapeText`'s behaviour for every non-branded value, so switching a
|
|
681
|
+
* call site from one to the other never changes output unless the value
|
|
682
|
+
* is actually branded.
|
|
683
|
+
*/
|
|
684
|
+
export function escapeTextOrMarkup(value: unknown): string {
|
|
685
|
+
if (isBfMarkup(value)) return value[BF_MARKUP_BRAND]
|
|
686
|
+
return escapeText(value)
|
|
687
|
+
}
|
|
688
|
+
|
|
615
689
|
/**
|
|
616
690
|
* `escapeText`'s counterpart for a claimed 'markup' slot's REACTIVE write
|
|
617
691
|
* (slot unification A3 follow-up), where the value is a plain-JS expression
|
|
@@ -631,33 +705,53 @@ export function escapeText(value: unknown): string {
|
|
|
631
705
|
* before handing it to a 'markup' writer — NOT the preamble-region case
|
|
632
706
|
* (`stringify/loop.ts`), whose value is already-built HTML from a nested
|
|
633
707
|
* compiled render and must stay unescaped.
|
|
708
|
+
*
|
|
709
|
+
* A `bfMarkup()`-branded value (#2651) — a component prop re-read on every
|
|
710
|
+
* reactive re-run, e.g. `initChild`'s `get header() { return bfMarkup(...) }`
|
|
711
|
+
* getter — is unwrapped to its raw string for the same reason a `Node` is
|
|
712
|
+
* passed through untouched: the compiler already escaped its contents once
|
|
713
|
+
* during assembly, so re-escaping it (or, worse, `String()`-stringifying
|
|
714
|
+
* the wrapper object into `"[object Object]"`) would corrupt it. Checked
|
|
715
|
+
* before the `Node` branch since the two shapes are mutually exclusive.
|
|
634
716
|
*/
|
|
635
717
|
export function escapeTextOrNode(value: unknown): string | Node {
|
|
718
|
+
if (isBfMarkup(value)) return value[BF_MARKUP_BRAND]
|
|
636
719
|
if (typeof Node !== 'undefined' && value instanceof Node) return value
|
|
637
720
|
return escapeText(value)
|
|
638
721
|
}
|
|
639
722
|
|
|
640
723
|
const SVG_NS = 'http://www.w3.org/2000/svg'
|
|
724
|
+
const MATHML_NS = 'http://www.w3.org/1998/Math/MathML'
|
|
725
|
+
|
|
726
|
+
/** Synthetic wrap tag for a parent's namespace, or null when it's plain HTML. */
|
|
727
|
+
function namespaceWrapTagFor(parent: Element | null | undefined): 'svg' | 'math' | null {
|
|
728
|
+
if (!parent) return null
|
|
729
|
+
if (parent.namespaceURI === SVG_NS) return 'svg'
|
|
730
|
+
if (parent.namespaceURI === MATHML_NS) return 'math'
|
|
731
|
+
return null
|
|
732
|
+
}
|
|
641
733
|
|
|
642
734
|
/**
|
|
643
735
|
* Parse an HTML string into a DocumentFragment, safely escaping ">" in
|
|
644
736
|
* attribute values. All code that sets innerHTML on dynamic HTML should
|
|
645
737
|
* use this instead of raw innerHTML assignment.
|
|
646
738
|
*
|
|
647
|
-
* When `parent` is provided and lives in the SVG namespace, the
|
|
648
|
-
* is parsed under
|
|
649
|
-
* `<svg>...</svg>`; the wrapper's children are
|
|
650
|
-
* fragment so callers see the same shape as the
|
|
651
|
-
* this, dynamically-inserted SVG elements (e.g.,
|
|
652
|
-
* conditional drag preview
|
|
653
|
-
*
|
|
654
|
-
* Graph/DAG Editor block
|
|
739
|
+
* When `parent` is provided and lives in the SVG or MathML namespace, the
|
|
740
|
+
* markup is parsed under the matching foreign-content context by wrapping
|
|
741
|
+
* it in `<svg>...</svg>` / `<math>...</math>`; the wrapper's children are
|
|
742
|
+
* moved into the returned fragment so callers see the same shape as the
|
|
743
|
+
* HTML path. Without this, dynamically-inserted SVG/MathML elements (e.g.,
|
|
744
|
+
* a `<path>` in a conditional drag preview, or an `<mrow>` in a dynamic
|
|
745
|
+
* equation) end up as `HTMLUnknownElement` in the xhtml namespace and the
|
|
746
|
+
* SVG/MathML renderer ignores them. Surfaced by the Graph/DAG Editor block
|
|
747
|
+
* (#135); ported to MathML in #1096.
|
|
655
748
|
*/
|
|
656
749
|
export function parseHTML(html: string, parent?: Element | null): DocumentFragment {
|
|
657
750
|
const tpl = document.createElement('template')
|
|
658
751
|
const escaped = escapeAttrGt(html)
|
|
659
|
-
|
|
660
|
-
|
|
752
|
+
const wrapTag = namespaceWrapTagFor(parent)
|
|
753
|
+
if (wrapTag) {
|
|
754
|
+
tpl.innerHTML = `<${wrapTag}>${escaped}</${wrapTag}>`
|
|
661
755
|
const wrapper = tpl.content.firstElementChild
|
|
662
756
|
const frag = document.createDocumentFragment()
|
|
663
757
|
if (wrapper) {
|
package/src/runtime/index.ts
CHANGED
|
@@ -105,6 +105,14 @@ export {
|
|
|
105
105
|
escapeAttr,
|
|
106
106
|
escapeText,
|
|
107
107
|
escapeTextOrNode,
|
|
108
|
+
// JSX-element-as-prop markup brand (#2651) — compiler-emitted code only.
|
|
109
|
+
// NOT re-exported from the public `@barefootjs/client` top-level entry;
|
|
110
|
+
// see `bfMarkup`'s docstring in `component.ts` for why calling it
|
|
111
|
+
// directly from userland is unsafe.
|
|
112
|
+
bfMarkup,
|
|
113
|
+
isBfMarkup,
|
|
114
|
+
escapeTextOrMarkup,
|
|
115
|
+
type BfMarkup,
|
|
108
116
|
} from './component.ts'
|
|
109
117
|
|
|
110
118
|
// Spread props helpers
|