sibujs 3.4.0 → 4.0.0
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/LICENSE +21 -21
- package/README.md +118 -15
- package/dist/browser.cjs +410 -101
- package/dist/browser.d.cts +50 -5
- package/dist/browser.d.ts +50 -5
- package/dist/browser.js +8 -6
- package/dist/build.cjs +777 -385
- package/dist/build.js +15 -15
- package/dist/cdn.global.js +11 -7
- package/dist/{chunk-JCO7AHNU.js → chunk-3EKJK5FZ.js} +73 -34
- package/dist/chunk-4MFZMLUU.js +147 -0
- package/dist/chunk-52XFPGSN.js +123 -0
- package/dist/chunk-5INI7D2L.js +194 -0
- package/dist/{chunk-OAVXAFAY.js → chunk-6LG2T7LO.js} +5 -5
- package/dist/{chunk-OOUQUCNN.js → chunk-ACBT6UZS.js} +57 -22
- package/dist/{chunk-F7HW2NI5.js → chunk-AW6HPJ3L.js} +1 -1
- package/dist/chunk-DHDZ7IVN.js +109 -0
- package/dist/{chunk-JNGGM2XE.js → chunk-DQVUBVNX.js} +16 -25
- package/dist/{chunk-AXFWGY32.js → chunk-DR7H6UGM.js} +232 -67
- package/dist/{chunk-WSGLJYFI.js → chunk-E62UADKL.js} +9 -3
- package/dist/{chunk-3Z2NGWQI.js → chunk-ES2GERY2.js} +1 -1
- package/dist/{chunk-S3V6ZXPI.js → chunk-EWEE7NBF.js} +115 -41
- package/dist/{chunk-3DVGCW7O.js → chunk-F64ZPCFE.js} +8 -8
- package/dist/{chunk-APFRCIRI.js → chunk-GCSGGA3Q.js} +295 -198
- package/dist/{chunk-EX77FXTT.js → chunk-HYCCIYNS.js} +228 -51
- package/dist/{chunk-ELXMRSVN.js → chunk-NF3LYCQH.js} +259 -124
- package/dist/chunk-O3QQ3XOL.js +61 -0
- package/dist/{chunk-BUKYCWHX.js → chunk-PBQEW5VW.js} +14 -10
- package/dist/{chunk-H5FI5WDP.js → chunk-RRIDJQ5C.js} +3 -3
- package/dist/{chunk-S3NFJO6L.js → chunk-TIRZCERI.js} +36 -5
- package/dist/{chunk-ODXVQ3CS.js → chunk-VFHIVEPF.js} +309 -188
- package/dist/chunk-VPP2FONR.js +142 -0
- package/dist/{chunk-KZBEVFXZ.js → chunk-W55YHPEP.js} +5 -3
- package/dist/{chunk-FKQG7FTY.js → chunk-WN6WDFCB.js} +4 -4
- package/dist/{chunk-CEBWDD63.js → chunk-WOOMUJFT.js} +228 -86
- package/dist/{chunk-ITWCTZYH.js → chunk-Z2CE42DB.js} +19 -25
- package/dist/{contracts-ey_Qh8ef.d.cts → contracts-Hg6ITAEF.d.cts} +6 -6
- package/dist/{contracts-ey_Qh8ef.d.ts → contracts-Hg6ITAEF.d.ts} +6 -6
- package/dist/{customElement-CPfIrbvg.d.ts → customElement-CKLoO63w.d.cts} +73 -11
- package/dist/{customElement-CPfIrbvg.d.cts → customElement-CKLoO63w.d.ts} +73 -11
- package/dist/data.cjs +483 -205
- package/dist/data.d.cts +139 -7
- package/dist/data.d.ts +139 -7
- package/dist/data.js +9 -9
- package/dist/devtools.cjs +222 -87
- package/dist/devtools.js +8 -8
- package/dist/dispose-4FZ6OFXR.js +19 -0
- package/dist/ecosystem.cjs +419 -175
- package/dist/ecosystem.js +11 -11
- package/dist/extras.cjs +1981 -765
- package/dist/extras.d.cts +7 -7
- package/dist/extras.d.ts +7 -7
- package/dist/extras.js +29 -26
- package/dist/index.cjs +784 -385
- package/dist/index.d.cts +299 -28
- package/dist/index.d.ts +299 -28
- package/dist/index.js +33 -18
- package/dist/motion.cjs +180 -50
- package/dist/motion.d.cts +26 -0
- package/dist/motion.d.ts +26 -0
- package/dist/motion.js +5 -5
- package/dist/patterns.cjs +437 -170
- package/dist/patterns.d.cts +60 -13
- package/dist/patterns.d.ts +60 -13
- package/dist/patterns.js +7 -7
- package/dist/performance.cjs +333 -148
- package/dist/performance.d.cts +55 -7
- package/dist/performance.d.ts +55 -7
- package/dist/performance.js +9 -9
- package/dist/plugins.cjs +1374 -576
- package/dist/plugins.d.cts +227 -9
- package/dist/plugins.d.ts +227 -9
- package/dist/plugins.js +613 -321
- package/dist/{ssr-D62yFwuw.d.cts → ssr-BiPRdZ6n.d.cts} +44 -15
- package/dist/{ssr-D62yFwuw.d.ts → ssr-BiPRdZ6n.d.ts} +44 -15
- package/dist/{ssr-2PPULEK2.js → ssr-JFP5535P.js} +5 -4
- package/dist/ssr.cjs +1104 -443
- package/dist/ssr.d.cts +230 -20
- package/dist/ssr.d.ts +230 -20
- package/dist/ssr.js +15 -12
- package/dist/{startup-0Qv6aosO.d.cts → startup-BMpaiMhP.d.cts} +1 -1
- package/dist/{startup-0Qv6aosO.d.ts → startup-BMpaiMhP.d.ts} +1 -1
- package/dist/testing.cjs +205 -63
- package/dist/testing.d.cts +1 -1
- package/dist/testing.d.ts +1 -1
- package/dist/testing.js +8 -10
- package/dist/ui.cjs +640 -199
- package/dist/ui.d.cts +2 -2
- package/dist/ui.d.ts +2 -2
- package/dist/ui.js +10 -10
- package/dist/widgets.cjs +207 -82
- package/dist/widgets.js +9 -9
- package/package.json +12 -7
- package/dist/chunk-5VGSK6D2.js +0 -80
- package/dist/chunk-COY6PUD2.js +0 -34
- package/dist/chunk-K35BAR4P.js +0 -96
- package/dist/chunk-L3GAGWCC.js +0 -111
- package/dist/chunk-RT3IYFN2.js +0 -38
|
@@ -32,7 +32,7 @@ declare function withWrapper<P>(WrappedComponent: Component<P>, wrapper: (compon
|
|
|
32
32
|
* Button("Click"); // type="button", disabled=false automatically
|
|
33
33
|
* ```
|
|
34
34
|
*/
|
|
35
|
-
declare function withDefaults<P extends
|
|
35
|
+
declare function withDefaults<P extends object>(component: Component<P>, defaults: Partial<P>): Component<Partial<P>>;
|
|
36
36
|
/**
|
|
37
37
|
* Composes multiple HOC wrappers into a single wrapper.
|
|
38
38
|
* Applied from right to left (like function composition).
|
|
@@ -117,7 +117,7 @@ type WithNodes<Props> = Props & {
|
|
|
117
117
|
* // Usage: Button({ label: 'Click me' }) — TypeScript infers props
|
|
118
118
|
* ```
|
|
119
119
|
*/
|
|
120
|
-
declare function defineComponent<Props extends
|
|
120
|
+
declare function defineComponent<Props extends object>(config: {
|
|
121
121
|
defaults?: Partial<Props>;
|
|
122
122
|
setup: (props: Props) => HTMLElement;
|
|
123
123
|
}): (props: Props) => HTMLElement;
|
|
@@ -148,7 +148,7 @@ declare function defineComponent<Props extends Record<string, unknown>>(config:
|
|
|
148
148
|
* // Usage: Card({ title: 'Hello', nodes: p('World') })
|
|
149
149
|
* ```
|
|
150
150
|
*/
|
|
151
|
-
declare function defineSlottedComponent<Props extends
|
|
151
|
+
declare function defineSlottedComponent<Props extends object>(config: {
|
|
152
152
|
defaults?: Partial<Props>;
|
|
153
153
|
setup: (props: WithNodes<Props>) => HTMLElement;
|
|
154
154
|
}): (props: WithNodes<Props>) => HTMLElement;
|
|
@@ -177,7 +177,7 @@ declare function defineSlottedComponent<Props extends Record<string, unknown>>(c
|
|
|
177
177
|
* // Usage: SmallIconButton({ icon: 'star', label: 'Favorite' })
|
|
178
178
|
* ```
|
|
179
179
|
*/
|
|
180
|
-
declare function withProps<OuterProps extends
|
|
180
|
+
declare function withProps<OuterProps extends object, InnerProps extends object>(component: (props: InnerProps) => HTMLElement, mapProps: (outer: OuterProps) => InnerProps): (props: OuterProps) => HTMLElement;
|
|
181
181
|
|
|
182
182
|
/**
|
|
183
183
|
* Runtime prop validation and strict typing contracts for SibuJS.
|
|
@@ -216,12 +216,12 @@ type PropSchema<Props> = {
|
|
|
216
216
|
* In production mode (process.env.NODE_ENV === 'production'), validation is skipped
|
|
217
217
|
* and only defaults are applied for performance.
|
|
218
218
|
*/
|
|
219
|
-
declare function validateProps<Props extends
|
|
219
|
+
declare function validateProps<Props extends object>(props: Partial<Props>, schema: PropSchema<Props>): Props;
|
|
220
220
|
/**
|
|
221
221
|
* Define a component with runtime prop validation.
|
|
222
222
|
* Validates props in development mode, applies defaults, then calls setup.
|
|
223
223
|
*/
|
|
224
|
-
declare function defineStrictComponent<Props extends
|
|
224
|
+
declare function defineStrictComponent<Props extends object>(config: {
|
|
225
225
|
name: string;
|
|
226
226
|
props: PropSchema<Props>;
|
|
227
227
|
setup: (props: Props) => HTMLElement;
|
|
@@ -3,7 +3,7 @@ interface FieldConfig<T = unknown> {
|
|
|
3
3
|
initial: T;
|
|
4
4
|
validators?: ValidatorFn<T>[];
|
|
5
5
|
}
|
|
6
|
-
type FormConfig<T extends
|
|
6
|
+
type FormConfig<T extends object> = {
|
|
7
7
|
[K in keyof T]: FieldConfig<T[K]>;
|
|
8
8
|
};
|
|
9
9
|
interface FormField<T = unknown> {
|
|
@@ -14,7 +14,7 @@ interface FormField<T = unknown> {
|
|
|
14
14
|
touch: () => void;
|
|
15
15
|
reset: () => void;
|
|
16
16
|
}
|
|
17
|
-
interface FormReturn<T extends
|
|
17
|
+
interface FormReturn<T extends object> {
|
|
18
18
|
fields: {
|
|
19
19
|
[K in keyof T]: FormField<T[K]>;
|
|
20
20
|
};
|
|
@@ -40,8 +40,18 @@ declare function custom<T>(fn: (value: T) => boolean, message: string): Validato
|
|
|
40
40
|
/**
|
|
41
41
|
* Props returned by bindField, ready to spread into an input tag factory.
|
|
42
42
|
*/
|
|
43
|
-
|
|
44
|
-
|
|
43
|
+
/**
|
|
44
|
+
* Props produced by {@link bindField}, ready to spread onto a tag factory.
|
|
45
|
+
*
|
|
46
|
+
* Generic over the field's value type. `value: () => unknown` forced every
|
|
47
|
+
* consumer to cast, because `unknown` does not satisfy the typed tag factories'
|
|
48
|
+
* `reactive<string>` — so the declaration contradicted this helper's own
|
|
49
|
+
* documented purpose ("props object ready to pass directly to a tag factory").
|
|
50
|
+
* The parameter defaults to `unknown`, so existing annotations of the bare
|
|
51
|
+
* `BoundFieldProps` keep compiling. (TYPE-010)
|
|
52
|
+
*/
|
|
53
|
+
interface BoundFieldProps<T = unknown> {
|
|
54
|
+
value: () => T;
|
|
45
55
|
on: {
|
|
46
56
|
input: (e: Event) => void;
|
|
47
57
|
change: (e: Event) => void;
|
|
@@ -69,8 +79,8 @@ interface BoundFieldProps {
|
|
|
69
79
|
* input(bindField(f.fields.email, { type: "email", placeholder: "Email" }))
|
|
70
80
|
* ```
|
|
71
81
|
*/
|
|
72
|
-
declare function bindField<T>(field: FormField<T>, extras?: Record<string, unknown>): BoundFieldProps
|
|
73
|
-
declare function form<T extends
|
|
82
|
+
declare function bindField<T>(field: FormField<T>, extras?: Record<string, unknown>): BoundFieldProps<T>;
|
|
83
|
+
declare function form<T extends object>(config: FormConfig<T>): FormReturn<T>;
|
|
74
84
|
|
|
75
85
|
interface VirtualListProps<T> {
|
|
76
86
|
items: () => T[];
|
|
@@ -195,25 +205,58 @@ declare function withScopedStyle<P>(css: string, component: (props: P) => HTMLEl
|
|
|
195
205
|
*/
|
|
196
206
|
declare function removeScopedStyle(scopeId: string): void;
|
|
197
207
|
|
|
208
|
+
/**
|
|
209
|
+
* Every value the shared attribute primitive accepts, and nothing more.
|
|
210
|
+
*
|
|
211
|
+
* `null` / `undefined` are part of the contract, not an oversight: they REMOVE
|
|
212
|
+
* the attribute. That is what makes the ordinary optional-value getter —
|
|
213
|
+
* `() => user?.label` typed `string | null | undefined` — expressible without a
|
|
214
|
+
* cast. The declared type used to exclude both while the runtime handled them,
|
|
215
|
+
* so the documented behaviour was unreachable from type-checked code.
|
|
216
|
+
*
|
|
217
|
+
* Deliberately NOT widened to `unknown`: the runtime only defines behaviour for
|
|
218
|
+
* these, and a public signature should describe the runtime exactly rather than
|
|
219
|
+
* inviting values whose handling is incidental.
|
|
220
|
+
*/
|
|
221
|
+
type AttributeValue = string | number | boolean | null | undefined;
|
|
222
|
+
/** An attribute value, or a reactive getter producing one. */
|
|
223
|
+
type AttributeSource = AttributeValue | (() => AttributeValue);
|
|
198
224
|
/**
|
|
199
225
|
* Bind multiple reactive attributes to an element.
|
|
200
226
|
* Each attribute value can be a static value or a reactive getter.
|
|
201
227
|
* Returns a single teardown function that stops all bindings.
|
|
228
|
+
*
|
|
229
|
+
* Static and reactive values share ONE security policy. They previously did
|
|
230
|
+
* not: a getter went through `bindAttribute` (which refuses `on*` and sanitizes
|
|
231
|
+
* URL/style/srcset), while a plain string went straight to `setAttribute`. So
|
|
232
|
+
* `bindAttrs(a, { href: "javascript:…" })` was live XSS while the identical
|
|
233
|
+
* `bindAttrs(a, { href: () => "javascript:…" })` was blocked — the same
|
|
234
|
+
* authoring intent with two different verdicts. Both now commit through
|
|
235
|
+
* `setSafeAttribute`.
|
|
202
236
|
*/
|
|
203
|
-
declare function bindAttrs(el: HTMLElement, attrs: Record<string,
|
|
237
|
+
declare function bindAttrs(el: HTMLElement, attrs: Record<string, AttributeSource>): () => void;
|
|
204
238
|
/**
|
|
205
239
|
* Reactively toggle a boolean attribute (like disabled, readonly, hidden).
|
|
206
240
|
* When the value is truthy the attribute is present (set to ""),
|
|
207
241
|
* when falsy the attribute is removed entirely.
|
|
208
242
|
* Returns a teardown function to stop reactive tracking.
|
|
243
|
+
*
|
|
244
|
+
* The attribute NAME is policed too: `bindBoolAttr(el, "onclick", true)` would
|
|
245
|
+
* otherwise create a live `onclick=""` handler slot through a helper whose
|
|
246
|
+
* whole purpose is inert presence toggling.
|
|
209
247
|
*/
|
|
210
248
|
declare function bindBoolAttr(el: HTMLElement, attr: string, getter: boolean | (() => boolean)): () => void;
|
|
211
249
|
/**
|
|
212
250
|
* Bind a data-* attribute reactively.
|
|
213
251
|
* Shorthand for `bindAttribute(el, "data-<key>", getter)`.
|
|
214
252
|
* Returns a teardown function to stop reactive tracking.
|
|
253
|
+
*
|
|
254
|
+
* Shares the removal semantics of every other attribute writer: `null` /
|
|
255
|
+
* `undefined` remove `data-<key>` rather than writing the text "null". The
|
|
256
|
+
* value is handed to the primitive unstringified so that decision is made in
|
|
257
|
+
* one place.
|
|
215
258
|
*/
|
|
216
|
-
declare function bindData(el: HTMLElement, key: string, getter:
|
|
259
|
+
declare function bindData(el: HTMLElement, key: string, getter: AttributeValue | (() => AttributeValue)): () => void;
|
|
217
260
|
|
|
218
261
|
/**
|
|
219
262
|
* Test-only helper to reset the module-level stack between specs. Client-only:
|
|
@@ -261,6 +304,15 @@ declare function toast(options?: {
|
|
|
261
304
|
/**
|
|
262
305
|
* infiniteScroll combines IntersectionObserver with a data-fetching trigger
|
|
263
306
|
* to implement infinite scroll behavior.
|
|
307
|
+
*
|
|
308
|
+
* ERROR CONTRACT: `onLoadMore` is user code and may reject. The observer
|
|
309
|
+
* callback cannot `await` it, so the promise it starts is floating — and a
|
|
310
|
+
* floating rejection is an unhandled rejection, which crashes a Node SSR
|
|
311
|
+
* process and fires `window.onunhandledrejection` in a browser, for what is
|
|
312
|
+
* really just a failed page of data. `loadMore()` therefore CONTAINS its own
|
|
313
|
+
* failure: it reports through the framework's central error pipeline
|
|
314
|
+
* (`reportError`, phase `"async"`) and never rejects to its caller. The
|
|
315
|
+
* `loading` flag is always cleared, so a failed page does not wedge the list.
|
|
264
316
|
*/
|
|
265
317
|
declare function infiniteScroll(options: {
|
|
266
318
|
onLoadMore: () => Promise<void>;
|
|
@@ -296,7 +348,7 @@ declare function pagination(options: {
|
|
|
296
348
|
* eventBus creates a typed publish/subscribe event system.
|
|
297
349
|
* No reactive state needed -- pure event dispatching.
|
|
298
350
|
*/
|
|
299
|
-
declare function eventBus<T extends
|
|
351
|
+
declare function eventBus<T extends object>(): {
|
|
300
352
|
on: <K extends keyof T>(event: K, handler: (data: T[K]) => void) => () => void;
|
|
301
353
|
emit: <K extends keyof T>(event: K, data: T[K]) => void;
|
|
302
354
|
off: <K extends keyof T>(event: K, handler: (data: T[K]) => void) => void;
|
|
@@ -308,7 +360,6 @@ interface CustomElementOptions {
|
|
|
308
360
|
mode?: "open" | "closed";
|
|
309
361
|
styles?: string;
|
|
310
362
|
observedAttributes?: string[];
|
|
311
|
-
extends?: string;
|
|
312
363
|
}
|
|
313
364
|
/**
|
|
314
365
|
* defineElement creates a Web Component wrapping a SibuJS component function.
|
|
@@ -316,7 +367,18 @@ interface CustomElementOptions {
|
|
|
316
367
|
declare function defineElement(name: string, component: (props: Record<string, unknown>, element: HTMLElement) => HTMLElement, options?: CustomElementOptions): void;
|
|
317
368
|
/**
|
|
318
369
|
* Creates an SVG element with proper namespace.
|
|
370
|
+
*
|
|
371
|
+
* Attribute writes go through the framework's shared commit primitive, so the
|
|
372
|
+
* SVG helper enforces exactly the policy the HTML tag factory and the reactive
|
|
373
|
+
* bindings enforce: `on*` strings are refused, `href` / `xlink:href` go through
|
|
374
|
+
* the URL allowlist, and `style` goes through the declaration-list sanitizer.
|
|
375
|
+
* Previously every non-function prop was a raw `setAttribute`, so
|
|
376
|
+
* `svgElement("svg", { onload: "alert(1)" })` installed a live handler that the
|
|
377
|
+
* equivalent HTML call had always refused.
|
|
378
|
+
*
|
|
379
|
+
* Function-valued `on*` props keep their existing meaning — `addEventListener`,
|
|
380
|
+
* never an attribute.
|
|
319
381
|
*/
|
|
320
382
|
declare function svgElement(tag: string, props?: Record<string, unknown>, ...nodes: (SVGElement | string)[]): SVGElement;
|
|
321
383
|
|
|
322
|
-
export {
|
|
384
|
+
export { type AttributeSource as A, type BoundFieldProps as B, type CustomElementOptions as C, intersection as D, lazyLoad as E, type FieldConfig as F, matchesPattern as G, max as H, type IntersectionResult as I, maxLength as J, min as K, minLength as L, type MaskOptions as M, pagination as N, phoneMask as O, removeScopedStyle as P, required as Q, scopedStyle as R, ssnMask as S, type Toast as T, svgElement as U, type ValidatorFn as V, timeMask as W, toast as X, withScopedStyle as Y, zipMask as Z, __resetDialogStack as _, type AttributeValue as a, FocusTrap as b, type FormConfig as c, type FormField as d, type FormReturn as e, type ToastInstance as f, VirtualList as g, type VirtualListProps as h, announce as i, aria as j, bindAttrs as k, bindBoolAttr as l, bindData as m, bindField as n, creditCardMask as o, custom as p, dateMask as q, defineElement as r, dialog as s, email as t, eventBus as u, focus as v, form as w, hotkey as x, infiniteScroll as y, inputMask as z };
|
|
@@ -3,7 +3,7 @@ interface FieldConfig<T = unknown> {
|
|
|
3
3
|
initial: T;
|
|
4
4
|
validators?: ValidatorFn<T>[];
|
|
5
5
|
}
|
|
6
|
-
type FormConfig<T extends
|
|
6
|
+
type FormConfig<T extends object> = {
|
|
7
7
|
[K in keyof T]: FieldConfig<T[K]>;
|
|
8
8
|
};
|
|
9
9
|
interface FormField<T = unknown> {
|
|
@@ -14,7 +14,7 @@ interface FormField<T = unknown> {
|
|
|
14
14
|
touch: () => void;
|
|
15
15
|
reset: () => void;
|
|
16
16
|
}
|
|
17
|
-
interface FormReturn<T extends
|
|
17
|
+
interface FormReturn<T extends object> {
|
|
18
18
|
fields: {
|
|
19
19
|
[K in keyof T]: FormField<T[K]>;
|
|
20
20
|
};
|
|
@@ -40,8 +40,18 @@ declare function custom<T>(fn: (value: T) => boolean, message: string): Validato
|
|
|
40
40
|
/**
|
|
41
41
|
* Props returned by bindField, ready to spread into an input tag factory.
|
|
42
42
|
*/
|
|
43
|
-
|
|
44
|
-
|
|
43
|
+
/**
|
|
44
|
+
* Props produced by {@link bindField}, ready to spread onto a tag factory.
|
|
45
|
+
*
|
|
46
|
+
* Generic over the field's value type. `value: () => unknown` forced every
|
|
47
|
+
* consumer to cast, because `unknown` does not satisfy the typed tag factories'
|
|
48
|
+
* `reactive<string>` — so the declaration contradicted this helper's own
|
|
49
|
+
* documented purpose ("props object ready to pass directly to a tag factory").
|
|
50
|
+
* The parameter defaults to `unknown`, so existing annotations of the bare
|
|
51
|
+
* `BoundFieldProps` keep compiling. (TYPE-010)
|
|
52
|
+
*/
|
|
53
|
+
interface BoundFieldProps<T = unknown> {
|
|
54
|
+
value: () => T;
|
|
45
55
|
on: {
|
|
46
56
|
input: (e: Event) => void;
|
|
47
57
|
change: (e: Event) => void;
|
|
@@ -69,8 +79,8 @@ interface BoundFieldProps {
|
|
|
69
79
|
* input(bindField(f.fields.email, { type: "email", placeholder: "Email" }))
|
|
70
80
|
* ```
|
|
71
81
|
*/
|
|
72
|
-
declare function bindField<T>(field: FormField<T>, extras?: Record<string, unknown>): BoundFieldProps
|
|
73
|
-
declare function form<T extends
|
|
82
|
+
declare function bindField<T>(field: FormField<T>, extras?: Record<string, unknown>): BoundFieldProps<T>;
|
|
83
|
+
declare function form<T extends object>(config: FormConfig<T>): FormReturn<T>;
|
|
74
84
|
|
|
75
85
|
interface VirtualListProps<T> {
|
|
76
86
|
items: () => T[];
|
|
@@ -195,25 +205,58 @@ declare function withScopedStyle<P>(css: string, component: (props: P) => HTMLEl
|
|
|
195
205
|
*/
|
|
196
206
|
declare function removeScopedStyle(scopeId: string): void;
|
|
197
207
|
|
|
208
|
+
/**
|
|
209
|
+
* Every value the shared attribute primitive accepts, and nothing more.
|
|
210
|
+
*
|
|
211
|
+
* `null` / `undefined` are part of the contract, not an oversight: they REMOVE
|
|
212
|
+
* the attribute. That is what makes the ordinary optional-value getter —
|
|
213
|
+
* `() => user?.label` typed `string | null | undefined` — expressible without a
|
|
214
|
+
* cast. The declared type used to exclude both while the runtime handled them,
|
|
215
|
+
* so the documented behaviour was unreachable from type-checked code.
|
|
216
|
+
*
|
|
217
|
+
* Deliberately NOT widened to `unknown`: the runtime only defines behaviour for
|
|
218
|
+
* these, and a public signature should describe the runtime exactly rather than
|
|
219
|
+
* inviting values whose handling is incidental.
|
|
220
|
+
*/
|
|
221
|
+
type AttributeValue = string | number | boolean | null | undefined;
|
|
222
|
+
/** An attribute value, or a reactive getter producing one. */
|
|
223
|
+
type AttributeSource = AttributeValue | (() => AttributeValue);
|
|
198
224
|
/**
|
|
199
225
|
* Bind multiple reactive attributes to an element.
|
|
200
226
|
* Each attribute value can be a static value or a reactive getter.
|
|
201
227
|
* Returns a single teardown function that stops all bindings.
|
|
228
|
+
*
|
|
229
|
+
* Static and reactive values share ONE security policy. They previously did
|
|
230
|
+
* not: a getter went through `bindAttribute` (which refuses `on*` and sanitizes
|
|
231
|
+
* URL/style/srcset), while a plain string went straight to `setAttribute`. So
|
|
232
|
+
* `bindAttrs(a, { href: "javascript:…" })` was live XSS while the identical
|
|
233
|
+
* `bindAttrs(a, { href: () => "javascript:…" })` was blocked — the same
|
|
234
|
+
* authoring intent with two different verdicts. Both now commit through
|
|
235
|
+
* `setSafeAttribute`.
|
|
202
236
|
*/
|
|
203
|
-
declare function bindAttrs(el: HTMLElement, attrs: Record<string,
|
|
237
|
+
declare function bindAttrs(el: HTMLElement, attrs: Record<string, AttributeSource>): () => void;
|
|
204
238
|
/**
|
|
205
239
|
* Reactively toggle a boolean attribute (like disabled, readonly, hidden).
|
|
206
240
|
* When the value is truthy the attribute is present (set to ""),
|
|
207
241
|
* when falsy the attribute is removed entirely.
|
|
208
242
|
* Returns a teardown function to stop reactive tracking.
|
|
243
|
+
*
|
|
244
|
+
* The attribute NAME is policed too: `bindBoolAttr(el, "onclick", true)` would
|
|
245
|
+
* otherwise create a live `onclick=""` handler slot through a helper whose
|
|
246
|
+
* whole purpose is inert presence toggling.
|
|
209
247
|
*/
|
|
210
248
|
declare function bindBoolAttr(el: HTMLElement, attr: string, getter: boolean | (() => boolean)): () => void;
|
|
211
249
|
/**
|
|
212
250
|
* Bind a data-* attribute reactively.
|
|
213
251
|
* Shorthand for `bindAttribute(el, "data-<key>", getter)`.
|
|
214
252
|
* Returns a teardown function to stop reactive tracking.
|
|
253
|
+
*
|
|
254
|
+
* Shares the removal semantics of every other attribute writer: `null` /
|
|
255
|
+
* `undefined` remove `data-<key>` rather than writing the text "null". The
|
|
256
|
+
* value is handed to the primitive unstringified so that decision is made in
|
|
257
|
+
* one place.
|
|
215
258
|
*/
|
|
216
|
-
declare function bindData(el: HTMLElement, key: string, getter:
|
|
259
|
+
declare function bindData(el: HTMLElement, key: string, getter: AttributeValue | (() => AttributeValue)): () => void;
|
|
217
260
|
|
|
218
261
|
/**
|
|
219
262
|
* Test-only helper to reset the module-level stack between specs. Client-only:
|
|
@@ -261,6 +304,15 @@ declare function toast(options?: {
|
|
|
261
304
|
/**
|
|
262
305
|
* infiniteScroll combines IntersectionObserver with a data-fetching trigger
|
|
263
306
|
* to implement infinite scroll behavior.
|
|
307
|
+
*
|
|
308
|
+
* ERROR CONTRACT: `onLoadMore` is user code and may reject. The observer
|
|
309
|
+
* callback cannot `await` it, so the promise it starts is floating — and a
|
|
310
|
+
* floating rejection is an unhandled rejection, which crashes a Node SSR
|
|
311
|
+
* process and fires `window.onunhandledrejection` in a browser, for what is
|
|
312
|
+
* really just a failed page of data. `loadMore()` therefore CONTAINS its own
|
|
313
|
+
* failure: it reports through the framework's central error pipeline
|
|
314
|
+
* (`reportError`, phase `"async"`) and never rejects to its caller. The
|
|
315
|
+
* `loading` flag is always cleared, so a failed page does not wedge the list.
|
|
264
316
|
*/
|
|
265
317
|
declare function infiniteScroll(options: {
|
|
266
318
|
onLoadMore: () => Promise<void>;
|
|
@@ -296,7 +348,7 @@ declare function pagination(options: {
|
|
|
296
348
|
* eventBus creates a typed publish/subscribe event system.
|
|
297
349
|
* No reactive state needed -- pure event dispatching.
|
|
298
350
|
*/
|
|
299
|
-
declare function eventBus<T extends
|
|
351
|
+
declare function eventBus<T extends object>(): {
|
|
300
352
|
on: <K extends keyof T>(event: K, handler: (data: T[K]) => void) => () => void;
|
|
301
353
|
emit: <K extends keyof T>(event: K, data: T[K]) => void;
|
|
302
354
|
off: <K extends keyof T>(event: K, handler: (data: T[K]) => void) => void;
|
|
@@ -308,7 +360,6 @@ interface CustomElementOptions {
|
|
|
308
360
|
mode?: "open" | "closed";
|
|
309
361
|
styles?: string;
|
|
310
362
|
observedAttributes?: string[];
|
|
311
|
-
extends?: string;
|
|
312
363
|
}
|
|
313
364
|
/**
|
|
314
365
|
* defineElement creates a Web Component wrapping a SibuJS component function.
|
|
@@ -316,7 +367,18 @@ interface CustomElementOptions {
|
|
|
316
367
|
declare function defineElement(name: string, component: (props: Record<string, unknown>, element: HTMLElement) => HTMLElement, options?: CustomElementOptions): void;
|
|
317
368
|
/**
|
|
318
369
|
* Creates an SVG element with proper namespace.
|
|
370
|
+
*
|
|
371
|
+
* Attribute writes go through the framework's shared commit primitive, so the
|
|
372
|
+
* SVG helper enforces exactly the policy the HTML tag factory and the reactive
|
|
373
|
+
* bindings enforce: `on*` strings are refused, `href` / `xlink:href` go through
|
|
374
|
+
* the URL allowlist, and `style` goes through the declaration-list sanitizer.
|
|
375
|
+
* Previously every non-function prop was a raw `setAttribute`, so
|
|
376
|
+
* `svgElement("svg", { onload: "alert(1)" })` installed a live handler that the
|
|
377
|
+
* equivalent HTML call had always refused.
|
|
378
|
+
*
|
|
379
|
+
* Function-valued `on*` props keep their existing meaning — `addEventListener`,
|
|
380
|
+
* never an attribute.
|
|
319
381
|
*/
|
|
320
382
|
declare function svgElement(tag: string, props?: Record<string, unknown>, ...nodes: (SVGElement | string)[]): SVGElement;
|
|
321
383
|
|
|
322
|
-
export {
|
|
384
|
+
export { type AttributeSource as A, type BoundFieldProps as B, type CustomElementOptions as C, intersection as D, lazyLoad as E, type FieldConfig as F, matchesPattern as G, max as H, type IntersectionResult as I, maxLength as J, min as K, minLength as L, type MaskOptions as M, pagination as N, phoneMask as O, removeScopedStyle as P, required as Q, scopedStyle as R, ssnMask as S, type Toast as T, svgElement as U, type ValidatorFn as V, timeMask as W, toast as X, withScopedStyle as Y, zipMask as Z, __resetDialogStack as _, type AttributeValue as a, FocusTrap as b, type FormConfig as c, type FormField as d, type FormReturn as e, type ToastInstance as f, VirtualList as g, type VirtualListProps as h, announce as i, aria as j, bindAttrs as k, bindBoolAttr as l, bindData as m, bindField as n, creditCardMask as o, custom as p, dateMask as q, defineElement as r, dialog as s, email as t, eventBus as u, focus as v, form as w, hotkey as x, infiniteScroll as y, inputMask as z };
|