sibujs 1.4.0 → 2.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/README.md +105 -119
- package/dist/browser.cjs +288 -80
- package/dist/browser.d.cts +19 -9
- package/dist/browser.d.ts +19 -9
- package/dist/browser.js +6 -6
- package/dist/build.cjs +1019 -313
- package/dist/build.d.cts +1 -1
- package/dist/build.d.ts +1 -1
- package/dist/build.js +15 -13
- package/dist/cdn.global.js +17 -16
- package/dist/chunk-2RA7SHDA.js +65 -0
- package/dist/chunk-2UPRY23K.js +80 -0
- package/dist/chunk-3JHCYHWN.js +125 -0
- package/dist/{chunk-ZWKZCBO6.js → chunk-3LR7GLWQ.js} +154 -33
- package/dist/{chunk-3AIRKM3B.js → chunk-3NSGB5JN.js} +115 -34
- package/dist/{chunk-3ARAQO7B.js → chunk-52YJLLRO.js} +29 -6
- package/dist/chunk-54EDRCEF.js +93 -0
- package/dist/chunk-7JDB7I65.js +1327 -0
- package/dist/{chunk-WZSPOOER.js → chunk-CC65Y57T.js} +8 -5
- package/dist/{chunk-23VV7YD3.js → chunk-DFPFITST.js} +25 -30
- package/dist/{chunk-WR5D4EGH.js → chunk-GTBNNBJ6.js} +14 -2
- package/dist/chunk-HB24TBAF.js +121 -0
- package/dist/{chunk-CZUGLNJS.js → chunk-ITX6OO3F.js} +3 -3
- package/dist/{chunk-JAKHTMQU.js → chunk-JA6667UN.js} +206 -46
- package/dist/{chunk-77L6NL3X.js → chunk-JXMMDLBY.js} +306 -183
- package/dist/{chunk-3X2YG6YM.js → chunk-JYD2PWXH.js} +59 -28
- package/dist/{chunk-F3FA4F32.js → chunk-KLRMB5ZS.js} +135 -79
- package/dist/{chunk-5X6PP2UK.js → chunk-LMLD24FC.js} +2 -2
- package/dist/{chunk-M4NLBH4I.js → chunk-LYTCUZ7H.js} +3 -2
- package/dist/{chunk-TSOKIX5Z.js → chunk-MIUAXB7K.js} +126 -74
- package/dist/{chunk-QWZG56ET.js → chunk-ND2664SF.js} +558 -190
- package/dist/{chunk-JCI5M6U6.js → chunk-O2MNQFLP.js} +261 -79
- package/dist/{chunk-EWFVA3TJ.js → chunk-R73P76YZ.js} +1 -1
- package/dist/{chunk-2BYQDGN3.js → chunk-SAHNHTFC.js} +234 -63
- package/dist/chunk-UCS6AMJ7.js +79 -0
- package/dist/{chunk-ZD6OAMTH.js → chunk-VLPPXTYG.js} +90 -35
- package/dist/{chunk-OUZZEE4S.js → chunk-WOMYAHHI.js} +17 -11
- package/dist/{contracts-xo5ckdRP.d.cts → contracts-ey_Qh8ef.d.cts} +7 -8
- package/dist/{contracts-xo5ckdRP.d.ts → contracts-ey_Qh8ef.d.ts} +7 -8
- package/dist/{customElement-D2DJp_xn.d.cts → customElement-CPfIrbvg.d.cts} +18 -9
- package/dist/{customElement-D2DJp_xn.d.ts → customElement-CPfIrbvg.d.ts} +18 -9
- package/dist/data.cjs +452 -100
- package/dist/data.d.cts +20 -2
- package/dist/data.d.ts +20 -2
- package/dist/data.js +11 -9
- package/dist/devtools.cjs +535 -247
- package/dist/devtools.d.cts +1 -1
- package/dist/devtools.d.ts +1 -1
- package/dist/devtools.js +34 -30
- package/dist/ecosystem.cjs +499 -143
- package/dist/ecosystem.d.cts +13 -11
- package/dist/ecosystem.d.ts +13 -11
- package/dist/ecosystem.js +12 -11
- package/dist/extras.cjs +3639 -1629
- package/dist/extras.d.cts +11 -11
- package/dist/extras.d.ts +11 -11
- package/dist/extras.js +58 -45
- package/dist/index.cjs +1023 -313
- package/dist/index.d.cts +128 -55
- package/dist/index.d.ts +128 -55
- package/dist/index.js +28 -16
- package/dist/{introspect-BumjnBKr.d.cts → introspect-BWNjNw64.d.cts} +22 -2
- package/dist/{introspect-CZrlcaYy.d.ts → introspect-cY2pg9pW.d.ts} +22 -2
- package/dist/motion.cjs +90 -36
- package/dist/motion.d.cts +1 -1
- package/dist/motion.d.ts +1 -1
- package/dist/motion.js +4 -4
- package/dist/patterns.cjs +414 -81
- package/dist/patterns.d.cts +53 -20
- package/dist/patterns.d.ts +53 -20
- package/dist/patterns.js +7 -7
- package/dist/performance.cjs +364 -108
- package/dist/performance.d.cts +29 -17
- package/dist/performance.d.ts +29 -17
- package/dist/performance.js +13 -6
- package/dist/plugin-D30wlGW5.d.cts +71 -0
- package/dist/plugin-D30wlGW5.d.ts +71 -0
- package/dist/plugins.cjs +652 -271
- package/dist/plugins.d.cts +13 -6
- package/dist/plugins.d.ts +13 -6
- package/dist/plugins.js +116 -50
- package/dist/{ssr-Do_SiVoL.d.cts → ssr-CrVNy6Pa.d.cts} +9 -15
- package/dist/{ssr-Do_SiVoL.d.ts → ssr-CrVNy6Pa.d.ts} +9 -15
- package/dist/{ssr-4PBXAOO3.js → ssr-FXD2PPMC.js} +4 -3
- package/dist/ssr.cjs +648 -219
- package/dist/ssr.d.cts +27 -7
- package/dist/ssr.d.ts +27 -7
- package/dist/ssr.js +12 -11
- package/dist/{tagFactory-DaJ0YWX6.d.ts → tagFactory-S17H2qxu.d.cts} +9 -1
- package/dist/{tagFactory-DaJ0YWX6.d.cts → tagFactory-S17H2qxu.d.ts} +9 -1
- package/dist/testing.cjs +252 -63
- package/dist/testing.d.cts +17 -4
- package/dist/testing.d.ts +17 -4
- package/dist/testing.js +100 -44
- package/dist/ui.cjs +576 -168
- package/dist/ui.d.cts +13 -16
- package/dist/ui.d.ts +13 -16
- package/dist/ui.js +20 -17
- package/dist/widgets.cjs +1001 -93
- package/dist/widgets.d.cts +104 -2
- package/dist/widgets.d.ts +104 -2
- package/dist/widgets.js +9 -7
- package/package.json +8 -2
- package/dist/chunk-32DY64NT.js +0 -282
- package/dist/chunk-3CRQALYP.js +0 -877
- package/dist/chunk-4EI4AG32.js +0 -482
- package/dist/chunk-4MYMUBRS.js +0 -21
- package/dist/chunk-6HLLIF3K.js +0 -398
- package/dist/chunk-6LSNVCS2.js +0 -937
- package/dist/chunk-6SA3QQES.js +0 -61
- package/dist/chunk-7BF6TK55.js +0 -1097
- package/dist/chunk-7TQKR4PP.js +0 -294
- package/dist/chunk-7V26P53V.js +0 -712
- package/dist/chunk-AZ3ISID5.js +0 -298
- package/dist/chunk-B7SWRFUT.js +0 -332
- package/dist/chunk-BGN5ZMP4.js +0 -26
- package/dist/chunk-BTU3TJDS.js +0 -365
- package/dist/chunk-BW3WT46K.js +0 -937
- package/dist/chunk-C6KFWOFV.js +0 -616
- package/dist/chunk-CHF5OHIA.js +0 -61
- package/dist/chunk-CHJ27IGK.js +0 -26
- package/dist/chunk-CMBFNA7L.js +0 -27
- package/dist/chunk-DAHRH4ON.js +0 -331
- package/dist/chunk-DKOHBI74.js +0 -924
- package/dist/chunk-DTCOOBMX.js +0 -725
- package/dist/chunk-EBGIRKQY.js +0 -616
- package/dist/chunk-EUZND3CB.js +0 -27
- package/dist/chunk-EVCZO745.js +0 -365
- package/dist/chunk-FGOEVHY3.js +0 -60
- package/dist/chunk-G3BOQPVO.js +0 -365
- package/dist/chunk-GCOK2LC3.js +0 -282
- package/dist/chunk-HGMJFBC7.js +0 -654
- package/dist/chunk-K5ZUMYVS.js +0 -89
- package/dist/chunk-KQPDEVVS.js +0 -398
- package/dist/chunk-L6JRBDNS.js +0 -60
- package/dist/chunk-LA6KQEDU.js +0 -712
- package/dist/chunk-MDVXJWFN.js +0 -304
- package/dist/chunk-MEZVEBPN.js +0 -2008
- package/dist/chunk-MK4ERFYL.js +0 -2249
- package/dist/chunk-MLKGABMK.js +0 -9
- package/dist/chunk-MQ5GOYPH.js +0 -2249
- package/dist/chunk-N6IZB6KJ.js +0 -567
- package/dist/chunk-NEKUBFPT.js +0 -60
- package/dist/chunk-NHUC2QWH.js +0 -282
- package/dist/chunk-NMRUZALC.js +0 -1097
- package/dist/chunk-NYVAC6P5.js +0 -37
- package/dist/chunk-OF7UZIVB.js +0 -725
- package/dist/chunk-P6W3STU4.js +0 -2249
- package/dist/chunk-PBHF5WKN.js +0 -616
- package/dist/chunk-PTQJDMRT.js +0 -146
- package/dist/chunk-PZEGYCF5.js +0 -61
- package/dist/chunk-QBMDLBU2.js +0 -975
- package/dist/chunk-RQGQSLQK.js +0 -725
- package/dist/chunk-SDLZDHKP.js +0 -107
- package/dist/chunk-TNQWPPE6.js +0 -37
- package/dist/chunk-UHNL42EF.js +0 -2730
- package/dist/chunk-UNXCEF6S.js +0 -21
- package/dist/chunk-V2XTI523.js +0 -347
- package/dist/chunk-VAU366PN.js +0 -2241
- package/dist/chunk-VMVDTCXB.js +0 -712
- package/dist/chunk-VRW3FULF.js +0 -725
- package/dist/chunk-WADYRCO2.js +0 -304
- package/dist/chunk-WILQZRO4.js +0 -282
- package/dist/chunk-WUHJISPP.js +0 -298
- package/dist/chunk-XYU6TZOW.js +0 -182
- package/dist/chunk-Y6GP4QGG.js +0 -276
- package/dist/chunk-YECR7UIA.js +0 -347
- package/dist/chunk-YUTWTI4B.js +0 -654
- package/dist/chunk-Z65KYU7I.js +0 -26
- package/dist/chunk-Z6POF5YC.js +0 -975
- package/dist/chunk-ZBJP6WFL.js +0 -482
- package/dist/contracts-DDrwxvJ-.d.cts +0 -245
- package/dist/contracts-DDrwxvJ-.d.ts +0 -245
- package/dist/contracts-DOrhwbke.d.cts +0 -245
- package/dist/contracts-DOrhwbke.d.ts +0 -245
- package/dist/customElement-BKQfbSZQ.d.cts +0 -262
- package/dist/customElement-BKQfbSZQ.d.ts +0 -262
- package/dist/customElement-yz8uyk-0.d.cts +0 -308
- package/dist/customElement-yz8uyk-0.d.ts +0 -308
- package/dist/introspect-Cb0zgpi2.d.cts +0 -477
- package/dist/introspect-Y2xNXGSf.d.ts +0 -477
- package/dist/plugin-Bek4RhJY.d.cts +0 -43
- package/dist/plugin-Bek4RhJY.d.ts +0 -43
- package/dist/ssr-3RXHP5ES.js +0 -38
- package/dist/ssr-6GIMY5MX.js +0 -38
- package/dist/ssr-BA6sxxUd.d.cts +0 -135
- package/dist/ssr-BA6sxxUd.d.ts +0 -135
- package/dist/ssr-WKUPVSSK.js +0 -36
- package/dist/tagFactory-Dl8QCLga.d.cts +0 -23
- package/dist/tagFactory-Dl8QCLga.d.ts +0 -23
package/dist/ecosystem.cjs
CHANGED
|
@@ -38,12 +38,12 @@ function isDev() {
|
|
|
38
38
|
var _isDev = isDev();
|
|
39
39
|
function devAssert(condition, message) {
|
|
40
40
|
if (_isDev && !condition) {
|
|
41
|
-
throw new Error(`[
|
|
41
|
+
throw new Error(`[SibuJS] ${message}`);
|
|
42
42
|
}
|
|
43
43
|
}
|
|
44
44
|
function devWarn(message) {
|
|
45
45
|
if (_isDev) {
|
|
46
|
-
console.warn(`[
|
|
46
|
+
console.warn(`[SibuJS] ${message}`);
|
|
47
47
|
}
|
|
48
48
|
}
|
|
49
49
|
|
|
@@ -53,11 +53,11 @@ var subscriberStack = new Array(32);
|
|
|
53
53
|
var stackCapacity = 32;
|
|
54
54
|
var stackTop = -1;
|
|
55
55
|
var currentSubscriber = null;
|
|
56
|
-
var signalSubscribers = /* @__PURE__ */ new WeakMap();
|
|
57
56
|
var SUBS = "__s";
|
|
58
57
|
var notifyDepth = 0;
|
|
59
58
|
var pendingQueue = [];
|
|
60
59
|
var pendingSet = /* @__PURE__ */ new Set();
|
|
60
|
+
var propagateStack = [];
|
|
61
61
|
function safeInvoke(sub) {
|
|
62
62
|
try {
|
|
63
63
|
sub();
|
|
@@ -66,6 +66,15 @@ function safeInvoke(sub) {
|
|
|
66
66
|
}
|
|
67
67
|
}
|
|
68
68
|
var trackingSuspended = false;
|
|
69
|
+
function retrack(effectFn, subscriber) {
|
|
70
|
+
const prev = currentSubscriber;
|
|
71
|
+
currentSubscriber = subscriber;
|
|
72
|
+
try {
|
|
73
|
+
effectFn();
|
|
74
|
+
} finally {
|
|
75
|
+
currentSubscriber = prev;
|
|
76
|
+
}
|
|
77
|
+
}
|
|
69
78
|
function track(effectFn, subscriber) {
|
|
70
79
|
if (!subscriber) subscriber = effectFn;
|
|
71
80
|
cleanup(subscriber);
|
|
@@ -104,7 +113,6 @@ function recordDependency(signal2) {
|
|
|
104
113
|
let subs = signal2[SUBS];
|
|
105
114
|
if (!subs) {
|
|
106
115
|
subs = /* @__PURE__ */ new Set();
|
|
107
|
-
signalSubscribers.set(signal2, subs);
|
|
108
116
|
signal2[SUBS] = subs;
|
|
109
117
|
}
|
|
110
118
|
subs.add(currentSubscriber);
|
|
@@ -126,57 +134,71 @@ function queueSignalNotification(signal2) {
|
|
|
126
134
|
}
|
|
127
135
|
}
|
|
128
136
|
}
|
|
137
|
+
var maxDrainIterations = 1e5;
|
|
129
138
|
function drainNotificationQueue() {
|
|
130
139
|
if (notifyDepth > 0) return;
|
|
131
140
|
notifyDepth++;
|
|
132
141
|
try {
|
|
133
142
|
let i = 0;
|
|
134
143
|
while (i < pendingQueue.length) {
|
|
144
|
+
if (i >= maxDrainIterations) {
|
|
145
|
+
if (typeof console !== "undefined") {
|
|
146
|
+
console.error(
|
|
147
|
+
`[SibuJS] Notification queue exceeded ${maxDrainIterations} iterations \u2014 likely an effect that writes to a signal it reads. Breaking to prevent infinite loop.`
|
|
148
|
+
);
|
|
149
|
+
}
|
|
150
|
+
break;
|
|
151
|
+
}
|
|
135
152
|
safeInvoke(pendingQueue[i]);
|
|
136
153
|
i++;
|
|
137
154
|
}
|
|
138
155
|
} finally {
|
|
139
|
-
pendingQueue.length = 0;
|
|
140
|
-
pendingSet.clear();
|
|
141
156
|
notifyDepth--;
|
|
157
|
+
if (notifyDepth === 0) {
|
|
158
|
+
pendingQueue.length = 0;
|
|
159
|
+
pendingSet.clear();
|
|
160
|
+
}
|
|
142
161
|
}
|
|
143
162
|
}
|
|
144
163
|
function propagateDirty(sub) {
|
|
145
164
|
sub();
|
|
146
|
-
|
|
147
|
-
|
|
165
|
+
const rootSig = sub._sig;
|
|
166
|
+
if (!rootSig) return;
|
|
167
|
+
const stack = propagateStack;
|
|
168
|
+
const baseLen = stack.length;
|
|
169
|
+
stack.push(rootSig);
|
|
170
|
+
while (stack.length > baseLen) {
|
|
171
|
+
const sig = stack.pop();
|
|
148
172
|
const first = sig.__f;
|
|
149
173
|
if (first) {
|
|
150
174
|
if (first._c) {
|
|
151
175
|
const nSig = first._sig;
|
|
152
|
-
nSig._d
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
if (!pendingSet.has(first)) {
|
|
176
|
+
if (!nSig._d) {
|
|
177
|
+
nSig._d = true;
|
|
178
|
+
stack.push(nSig);
|
|
179
|
+
}
|
|
180
|
+
} else if (!pendingSet.has(first)) {
|
|
157
181
|
pendingSet.add(first);
|
|
158
182
|
pendingQueue.push(first);
|
|
159
183
|
}
|
|
160
|
-
|
|
184
|
+
continue;
|
|
161
185
|
}
|
|
162
186
|
const subs = sig[SUBS];
|
|
163
|
-
if (!subs)
|
|
164
|
-
let nextSig;
|
|
187
|
+
if (!subs) continue;
|
|
165
188
|
for (const s of subs) {
|
|
166
189
|
if (s._c) {
|
|
167
|
-
s();
|
|
168
190
|
const nSig = s._sig;
|
|
169
|
-
if (nSig && !
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
191
|
+
if (nSig && !nSig._d) {
|
|
192
|
+
nSig._d = true;
|
|
193
|
+
stack.push(nSig);
|
|
194
|
+
} else if (!nSig) {
|
|
195
|
+
s();
|
|
173
196
|
}
|
|
174
197
|
} else if (!pendingSet.has(s)) {
|
|
175
198
|
pendingSet.add(s);
|
|
176
199
|
pendingQueue.push(s);
|
|
177
200
|
}
|
|
178
201
|
}
|
|
179
|
-
sig = nextSig;
|
|
180
202
|
}
|
|
181
203
|
}
|
|
182
204
|
function notifySubscribers(signal2) {
|
|
@@ -200,13 +222,23 @@ function notifySubscribers(signal2) {
|
|
|
200
222
|
}
|
|
201
223
|
let i = 0;
|
|
202
224
|
while (i < pendingQueue.length) {
|
|
225
|
+
if (i >= maxDrainIterations) {
|
|
226
|
+
if (typeof console !== "undefined") {
|
|
227
|
+
console.error(
|
|
228
|
+
`[SibuJS] Notification queue exceeded ${maxDrainIterations} iterations \u2014 likely an effect that writes to a signal it reads. Breaking to prevent infinite loop.`
|
|
229
|
+
);
|
|
230
|
+
}
|
|
231
|
+
break;
|
|
232
|
+
}
|
|
203
233
|
safeInvoke(pendingQueue[i]);
|
|
204
234
|
i++;
|
|
205
235
|
}
|
|
206
236
|
} finally {
|
|
207
|
-
pendingQueue.length = 0;
|
|
208
|
-
pendingSet.clear();
|
|
209
237
|
notifyDepth--;
|
|
238
|
+
if (notifyDepth === 0) {
|
|
239
|
+
pendingQueue.length = 0;
|
|
240
|
+
pendingSet.clear();
|
|
241
|
+
}
|
|
210
242
|
}
|
|
211
243
|
return;
|
|
212
244
|
}
|
|
@@ -226,30 +258,48 @@ function notifySubscribers(signal2) {
|
|
|
226
258
|
notifyDepth++;
|
|
227
259
|
try {
|
|
228
260
|
let directCount = 0;
|
|
261
|
+
let hasComputedSub = false;
|
|
229
262
|
for (const sub of subs) {
|
|
263
|
+
if (sub._c) hasComputedSub = true;
|
|
230
264
|
pendingQueue[directCount++] = sub;
|
|
231
265
|
}
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
266
|
+
if (!hasComputedSub) {
|
|
267
|
+
for (let i2 = 0; i2 < directCount; i2++) {
|
|
268
|
+
safeInvoke(pendingQueue[i2]);
|
|
235
269
|
}
|
|
236
|
-
}
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
270
|
+
} else {
|
|
271
|
+
for (let i2 = 0; i2 < directCount; i2++) {
|
|
272
|
+
if (pendingQueue[i2]._c) {
|
|
273
|
+
propagateDirty(pendingQueue[i2]);
|
|
274
|
+
}
|
|
275
|
+
}
|
|
276
|
+
for (let i2 = 0; i2 < directCount; i2++) {
|
|
277
|
+
const sub = pendingQueue[i2];
|
|
278
|
+
if (!sub._c && !pendingSet.has(sub)) {
|
|
279
|
+
pendingSet.add(sub);
|
|
280
|
+
safeInvoke(sub);
|
|
241
281
|
}
|
|
242
282
|
}
|
|
243
283
|
}
|
|
244
284
|
let i = directCount;
|
|
245
285
|
while (i < pendingQueue.length) {
|
|
286
|
+
if (i - directCount >= maxDrainIterations) {
|
|
287
|
+
if (typeof console !== "undefined") {
|
|
288
|
+
console.error(
|
|
289
|
+
`[SibuJS] Notification queue exceeded ${maxDrainIterations} iterations \u2014 likely an effect that writes to a signal it reads. Breaking to prevent infinite loop.`
|
|
290
|
+
);
|
|
291
|
+
}
|
|
292
|
+
break;
|
|
293
|
+
}
|
|
246
294
|
safeInvoke(pendingQueue[i]);
|
|
247
295
|
i++;
|
|
248
296
|
}
|
|
249
297
|
} finally {
|
|
250
|
-
pendingQueue.length = 0;
|
|
251
|
-
pendingSet.clear();
|
|
252
298
|
notifyDepth--;
|
|
299
|
+
if (notifyDepth === 0) {
|
|
300
|
+
pendingQueue.length = 0;
|
|
301
|
+
pendingSet.clear();
|
|
302
|
+
}
|
|
253
303
|
}
|
|
254
304
|
}
|
|
255
305
|
function cleanup(subscriber) {
|
|
@@ -260,7 +310,9 @@ function cleanup(subscriber) {
|
|
|
260
310
|
if (subs) {
|
|
261
311
|
subs.delete(subscriber);
|
|
262
312
|
if (singleDep.__f === subscriber) {
|
|
263
|
-
singleDep.__f = void 0;
|
|
313
|
+
singleDep.__f = subs.size === 1 ? subs.values().next().value : void 0;
|
|
314
|
+
} else if (subs.size === 1 && singleDep.__f === void 0) {
|
|
315
|
+
singleDep.__f = subs.values().next().value;
|
|
264
316
|
}
|
|
265
317
|
}
|
|
266
318
|
sub._dep = void 0;
|
|
@@ -273,7 +325,9 @@ function cleanup(subscriber) {
|
|
|
273
325
|
if (subs) {
|
|
274
326
|
subs.delete(subscriber);
|
|
275
327
|
if (signal2.__f === subscriber) {
|
|
276
|
-
signal2.__f = void 0;
|
|
328
|
+
signal2.__f = subs.size === 1 ? subs.values().next().value : void 0;
|
|
329
|
+
} else if (subs.size === 1 && signal2.__f === void 0) {
|
|
330
|
+
signal2.__f = subs.values().next().value;
|
|
277
331
|
}
|
|
278
332
|
}
|
|
279
333
|
}
|
|
@@ -281,9 +335,28 @@ function cleanup(subscriber) {
|
|
|
281
335
|
}
|
|
282
336
|
|
|
283
337
|
// src/core/ssr-context.ts
|
|
284
|
-
var
|
|
338
|
+
var als = null;
|
|
339
|
+
try {
|
|
340
|
+
if (typeof process !== "undefined" && process.versions && process.versions.node) {
|
|
341
|
+
const req = Function("return typeof require==='function'?require:null")();
|
|
342
|
+
if (req) {
|
|
343
|
+
const mod = req("node:async_hooks");
|
|
344
|
+
als = new mod.AsyncLocalStorage();
|
|
345
|
+
}
|
|
346
|
+
}
|
|
347
|
+
} catch {
|
|
348
|
+
als = null;
|
|
349
|
+
}
|
|
350
|
+
var fallbackStore = { ssr: false, suspenseIdCounter: 0 };
|
|
351
|
+
function getSSRStore() {
|
|
352
|
+
if (als) {
|
|
353
|
+
const s = als.getStore();
|
|
354
|
+
if (s) return s;
|
|
355
|
+
}
|
|
356
|
+
return fallbackStore;
|
|
357
|
+
}
|
|
285
358
|
function isSSR() {
|
|
286
|
-
return
|
|
359
|
+
return getSSRStore().ssr;
|
|
287
360
|
}
|
|
288
361
|
|
|
289
362
|
// src/core/signals/effect.ts
|
|
@@ -293,26 +366,86 @@ function effect(effectFn, options) {
|
|
|
293
366
|
if (isSSR()) return () => {
|
|
294
367
|
};
|
|
295
368
|
const onError = options?.onError;
|
|
369
|
+
let userCleanups = [];
|
|
370
|
+
const onCleanup = (fn) => {
|
|
371
|
+
userCleanups.push(fn);
|
|
372
|
+
};
|
|
373
|
+
const runUserCleanups = () => {
|
|
374
|
+
if (userCleanups.length === 0) return;
|
|
375
|
+
const list = userCleanups;
|
|
376
|
+
userCleanups = [];
|
|
377
|
+
for (let i = list.length - 1; i >= 0; i--) {
|
|
378
|
+
try {
|
|
379
|
+
list[i]();
|
|
380
|
+
} catch (err) {
|
|
381
|
+
if (typeof console !== "undefined") {
|
|
382
|
+
console.warn("[SibuJS effect] onCleanup threw:", err);
|
|
383
|
+
}
|
|
384
|
+
}
|
|
385
|
+
}
|
|
386
|
+
};
|
|
387
|
+
const invokeBody = () => effectFn(onCleanup);
|
|
296
388
|
const wrappedFn = onError ? () => {
|
|
297
389
|
try {
|
|
298
|
-
|
|
390
|
+
invokeBody();
|
|
299
391
|
} catch (err) {
|
|
300
392
|
onError(err);
|
|
301
393
|
}
|
|
302
|
-
} :
|
|
394
|
+
} : invokeBody;
|
|
303
395
|
let cleanupHandle = () => {
|
|
304
396
|
};
|
|
397
|
+
let running = false;
|
|
305
398
|
const subscriber = () => {
|
|
306
|
-
|
|
307
|
-
|
|
399
|
+
if (running) {
|
|
400
|
+
if (_g.__SIBU_DEV_WARN__ !== false && typeof console !== "undefined") {
|
|
401
|
+
console.warn(
|
|
402
|
+
"[SibuJS] effect re-entered itself while running \u2014 the triggering update will be ignored. Wrap mutual writes in `batch()` or split the effect to avoid this."
|
|
403
|
+
);
|
|
404
|
+
}
|
|
405
|
+
return;
|
|
406
|
+
}
|
|
407
|
+
running = true;
|
|
408
|
+
try {
|
|
409
|
+
runUserCleanups();
|
|
410
|
+
cleanupHandle();
|
|
411
|
+
cleanupHandle = track(wrappedFn, subscriber);
|
|
412
|
+
} finally {
|
|
413
|
+
running = false;
|
|
414
|
+
}
|
|
308
415
|
};
|
|
309
|
-
|
|
416
|
+
running = true;
|
|
417
|
+
try {
|
|
418
|
+
cleanupHandle = track(wrappedFn, subscriber);
|
|
419
|
+
} finally {
|
|
420
|
+
running = false;
|
|
421
|
+
}
|
|
310
422
|
const hook = _g.__SIBU_DEVTOOLS_GLOBAL_HOOK__;
|
|
311
423
|
if (hook) hook.emit("effect:create", { effectFn });
|
|
424
|
+
let disposed = false;
|
|
312
425
|
return () => {
|
|
426
|
+
if (disposed) return;
|
|
427
|
+
disposed = true;
|
|
313
428
|
const h = _g.__SIBU_DEVTOOLS_GLOBAL_HOOK__;
|
|
314
|
-
if (h)
|
|
315
|
-
|
|
429
|
+
if (h) {
|
|
430
|
+
try {
|
|
431
|
+
h.emit("effect:destroy", { effectFn });
|
|
432
|
+
} catch {
|
|
433
|
+
}
|
|
434
|
+
}
|
|
435
|
+
try {
|
|
436
|
+
runUserCleanups();
|
|
437
|
+
} catch (err) {
|
|
438
|
+
if (typeof console !== "undefined") {
|
|
439
|
+
console.warn("[SibuJS effect] onCleanup threw during dispose:", err);
|
|
440
|
+
}
|
|
441
|
+
}
|
|
442
|
+
try {
|
|
443
|
+
cleanupHandle();
|
|
444
|
+
} catch (err) {
|
|
445
|
+
if (typeof console !== "undefined") {
|
|
446
|
+
console.warn("[SibuJS effect] dispose threw:", err);
|
|
447
|
+
}
|
|
448
|
+
}
|
|
316
449
|
};
|
|
317
450
|
}
|
|
318
451
|
|
|
@@ -336,10 +469,13 @@ function enqueueBatchedSignal(signal2) {
|
|
|
336
469
|
return true;
|
|
337
470
|
}
|
|
338
471
|
function flushBatch() {
|
|
339
|
-
|
|
340
|
-
|
|
472
|
+
try {
|
|
473
|
+
for (const signal2 of pendingSignals) {
|
|
474
|
+
queueSignalNotification(signal2);
|
|
475
|
+
}
|
|
476
|
+
} finally {
|
|
477
|
+
pendingSignals.clear();
|
|
341
478
|
}
|
|
342
|
-
pendingSignals.clear();
|
|
343
479
|
drainNotificationQueue();
|
|
344
480
|
}
|
|
345
481
|
|
|
@@ -382,6 +518,85 @@ function signal(initial, options) {
|
|
|
382
518
|
}
|
|
383
519
|
|
|
384
520
|
// src/plugins/plugin.ts
|
|
521
|
+
function createPluginRegistry() {
|
|
522
|
+
const installedPlugins = /* @__PURE__ */ new Set();
|
|
523
|
+
const hooks = { init: [], mount: [], unmount: [], error: [] };
|
|
524
|
+
const provided = /* @__PURE__ */ new Map();
|
|
525
|
+
const registry = {
|
|
526
|
+
installedPlugins,
|
|
527
|
+
hooks,
|
|
528
|
+
provided,
|
|
529
|
+
plugin(p, options) {
|
|
530
|
+
if (installedPlugins.has(p.name)) {
|
|
531
|
+
console.warn(`[Plugin] "${p.name}" is already installed.`);
|
|
532
|
+
return;
|
|
533
|
+
}
|
|
534
|
+
const ctx = {
|
|
535
|
+
onInit: (cb) => hooks.init.push(cb),
|
|
536
|
+
onMount: (cb) => hooks.mount.push(cb),
|
|
537
|
+
onUnmount: (cb) => hooks.unmount.push(cb),
|
|
538
|
+
onError: (cb) => hooks.error.push(cb),
|
|
539
|
+
provide: (key, value) => provided.set(key, value)
|
|
540
|
+
};
|
|
541
|
+
const initHooksBefore = hooks.init.length;
|
|
542
|
+
p.install(ctx, options);
|
|
543
|
+
installedPlugins.add(p.name);
|
|
544
|
+
const justAdded = hooks.init.slice(initHooksBefore);
|
|
545
|
+
for (const cb of justAdded) {
|
|
546
|
+
try {
|
|
547
|
+
cb();
|
|
548
|
+
} catch (e) {
|
|
549
|
+
console.error(`[Plugin] "${p.name}" init error:`, e);
|
|
550
|
+
}
|
|
551
|
+
}
|
|
552
|
+
},
|
|
553
|
+
inject(key, defaultValue) {
|
|
554
|
+
if (provided.has(key)) return provided.get(key);
|
|
555
|
+
if (defaultValue !== void 0) return defaultValue;
|
|
556
|
+
throw new Error(`[Plugin] No provider found for key "${key}"`);
|
|
557
|
+
},
|
|
558
|
+
triggerMount(element) {
|
|
559
|
+
const snapshot = hooks.mount.slice();
|
|
560
|
+
for (const hook of snapshot) {
|
|
561
|
+
try {
|
|
562
|
+
hook(element);
|
|
563
|
+
} catch (e) {
|
|
564
|
+
console.error("[Plugin] Mount hook error:", e);
|
|
565
|
+
}
|
|
566
|
+
}
|
|
567
|
+
},
|
|
568
|
+
triggerUnmount(element) {
|
|
569
|
+
const snapshot = hooks.unmount.slice();
|
|
570
|
+
for (const hook of snapshot) {
|
|
571
|
+
try {
|
|
572
|
+
hook(element);
|
|
573
|
+
} catch (e) {
|
|
574
|
+
console.error("[Plugin] Unmount hook error:", e);
|
|
575
|
+
}
|
|
576
|
+
}
|
|
577
|
+
},
|
|
578
|
+
triggerError(error) {
|
|
579
|
+
const snapshot = hooks.error.slice();
|
|
580
|
+
for (const hook of snapshot) {
|
|
581
|
+
try {
|
|
582
|
+
hook(error);
|
|
583
|
+
} catch (e) {
|
|
584
|
+
console.error("[Plugin] Error hook error:", e);
|
|
585
|
+
}
|
|
586
|
+
}
|
|
587
|
+
},
|
|
588
|
+
reset() {
|
|
589
|
+
installedPlugins.clear();
|
|
590
|
+
hooks.init.length = 0;
|
|
591
|
+
hooks.mount.length = 0;
|
|
592
|
+
hooks.unmount.length = 0;
|
|
593
|
+
hooks.error.length = 0;
|
|
594
|
+
provided.clear();
|
|
595
|
+
}
|
|
596
|
+
};
|
|
597
|
+
return registry;
|
|
598
|
+
}
|
|
599
|
+
var defaultRegistry = createPluginRegistry();
|
|
385
600
|
function createPlugin(name, install) {
|
|
386
601
|
return { name, install };
|
|
387
602
|
}
|
|
@@ -392,7 +607,7 @@ function mobXAdapter(options) {
|
|
|
392
607
|
const { autorun } = options;
|
|
393
608
|
const disposers = [];
|
|
394
609
|
function fromMobX(expression) {
|
|
395
|
-
const [getValue, setValue] = signal(
|
|
610
|
+
const [getValue, setValue] = signal(void 0);
|
|
396
611
|
const disposer = autorun(() => {
|
|
397
612
|
const newValue = expression();
|
|
398
613
|
batch(() => {
|
|
@@ -400,7 +615,13 @@ function mobXAdapter(options) {
|
|
|
400
615
|
});
|
|
401
616
|
});
|
|
402
617
|
disposers.push(disposer);
|
|
403
|
-
|
|
618
|
+
const getter = (() => getValue());
|
|
619
|
+
getter.dispose = () => {
|
|
620
|
+
const i = disposers.indexOf(disposer);
|
|
621
|
+
if (i >= 0) disposers.splice(i, 1);
|
|
622
|
+
disposer();
|
|
623
|
+
};
|
|
624
|
+
return getter;
|
|
404
625
|
}
|
|
405
626
|
function toMobX(sibuGetter, callback) {
|
|
406
627
|
return effect(() => {
|
|
@@ -422,6 +643,7 @@ function mobXAdapter(options) {
|
|
|
422
643
|
function derived(getter, options) {
|
|
423
644
|
devAssert(typeof getter === "function", "derived: argument must be a getter function.");
|
|
424
645
|
const debugName = options?.name;
|
|
646
|
+
const equals = options?.equals;
|
|
425
647
|
const cs = {};
|
|
426
648
|
cs._d = false;
|
|
427
649
|
cs._g = getter;
|
|
@@ -432,25 +654,56 @@ function derived(getter, options) {
|
|
|
432
654
|
markDirty._c = 1;
|
|
433
655
|
markDirty._sig = cs;
|
|
434
656
|
track(() => {
|
|
435
|
-
|
|
436
|
-
|
|
657
|
+
let threw = true;
|
|
658
|
+
try {
|
|
659
|
+
cs._v = getter();
|
|
660
|
+
cs._d = false;
|
|
661
|
+
threw = false;
|
|
662
|
+
} finally {
|
|
663
|
+
if (threw) cs._d = true;
|
|
664
|
+
}
|
|
437
665
|
}, markDirty);
|
|
438
666
|
const hook = globalThis.__SIBU_DEVTOOLS_GLOBAL_HOOK__;
|
|
667
|
+
let evaluating = false;
|
|
439
668
|
function computedGetter() {
|
|
669
|
+
if (evaluating) {
|
|
670
|
+
throw new Error(
|
|
671
|
+
`[SibuJS] Circular dependency detected in derived${debugName ? ` "${debugName}"` : ""}. A derived signal cannot read itself (directly or through a chain).`
|
|
672
|
+
);
|
|
673
|
+
}
|
|
440
674
|
if (trackingSuspended) {
|
|
441
675
|
if (cs._d) {
|
|
442
|
-
|
|
443
|
-
|
|
676
|
+
evaluating = true;
|
|
677
|
+
let threw = true;
|
|
678
|
+
try {
|
|
679
|
+
retrack(() => {
|
|
680
|
+
cs._v = getter();
|
|
681
|
+
cs._d = false;
|
|
682
|
+
threw = false;
|
|
683
|
+
}, markDirty);
|
|
684
|
+
} finally {
|
|
685
|
+
evaluating = false;
|
|
686
|
+
if (threw) cs._d = true;
|
|
687
|
+
}
|
|
444
688
|
}
|
|
445
689
|
return cs._v;
|
|
446
690
|
}
|
|
447
691
|
recordDependency(cs);
|
|
448
692
|
if (cs._d) {
|
|
449
693
|
const oldValue = cs._v;
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
694
|
+
evaluating = true;
|
|
695
|
+
let threw = true;
|
|
696
|
+
try {
|
|
697
|
+
retrack(() => {
|
|
698
|
+
const next = getter();
|
|
699
|
+
cs._v = equals && cs._v !== void 0 ? equals(cs._v, next) ? cs._v : next : next;
|
|
700
|
+
cs._d = false;
|
|
701
|
+
threw = false;
|
|
702
|
+
}, markDirty);
|
|
703
|
+
} finally {
|
|
704
|
+
evaluating = false;
|
|
705
|
+
if (threw) cs._d = true;
|
|
706
|
+
}
|
|
454
707
|
if (hook && oldValue !== cs._v) {
|
|
455
708
|
hook.emit("computed:update", { signal: cs, oldValue, newValue: cs._v });
|
|
456
709
|
}
|
|
@@ -476,12 +729,12 @@ function reduxAdapter(options) {
|
|
|
476
729
|
setState(store.getState());
|
|
477
730
|
});
|
|
478
731
|
});
|
|
479
|
-
function
|
|
732
|
+
function select(selector) {
|
|
480
733
|
return derived(() => selector(getState()));
|
|
481
734
|
}
|
|
482
735
|
const api = {
|
|
483
736
|
getState,
|
|
484
|
-
|
|
737
|
+
select,
|
|
485
738
|
dispatch: store.dispatch.bind(store),
|
|
486
739
|
destroy: unsubscribe
|
|
487
740
|
};
|
|
@@ -499,12 +752,12 @@ function zustandAdapter(options) {
|
|
|
499
752
|
setSibuState(state);
|
|
500
753
|
});
|
|
501
754
|
});
|
|
502
|
-
function
|
|
755
|
+
function select(selector) {
|
|
503
756
|
return derived(() => selector(getState()));
|
|
504
757
|
}
|
|
505
758
|
const api = {
|
|
506
759
|
getState,
|
|
507
|
-
|
|
760
|
+
select,
|
|
508
761
|
setState: store.setState.bind(store),
|
|
509
762
|
destroy() {
|
|
510
763
|
unsubscribe();
|
|
@@ -516,29 +769,79 @@ function zustandAdapter(options) {
|
|
|
516
769
|
}
|
|
517
770
|
|
|
518
771
|
// src/utils/sanitize.ts
|
|
772
|
+
var SAFE_URL_PROTOCOLS = ["http:", "https:", "mailto:", "tel:", "ftp:"];
|
|
519
773
|
function sanitizeUrl(url) {
|
|
520
774
|
const trimmed = url.replace(/[\x00-\x20\x7f-\x9f]+/g, "").trim();
|
|
521
775
|
if (!trimmed) return "";
|
|
522
776
|
const lower = trimmed.toLowerCase();
|
|
523
|
-
|
|
524
|
-
|
|
777
|
+
let schemeEnd = -1;
|
|
778
|
+
for (let i = 0; i < lower.length; i++) {
|
|
779
|
+
const ch = lower.charCodeAt(i);
|
|
780
|
+
if (ch === 58) {
|
|
781
|
+
schemeEnd = i;
|
|
782
|
+
break;
|
|
783
|
+
}
|
|
784
|
+
if (ch === 47 || ch === 63 || ch === 35) break;
|
|
525
785
|
}
|
|
786
|
+
if (schemeEnd === -1) return trimmed;
|
|
787
|
+
const scheme = lower.slice(0, schemeEnd + 1);
|
|
788
|
+
if (!/^[a-z][a-z0-9+.-]*:$/.test(scheme)) return trimmed;
|
|
789
|
+
if (SAFE_URL_PROTOCOLS.indexOf(scheme) === -1) return "";
|
|
526
790
|
return trimmed;
|
|
527
791
|
}
|
|
792
|
+
function sanitizeSrcset(value) {
|
|
793
|
+
const parts = value.split(",");
|
|
794
|
+
const out = [];
|
|
795
|
+
for (let i = 0; i < parts.length; i++) {
|
|
796
|
+
const part = parts[i].trim();
|
|
797
|
+
if (!part) continue;
|
|
798
|
+
const m = part.match(/^(\S+)(\s+.+)?$/);
|
|
799
|
+
if (!m) continue;
|
|
800
|
+
const safe = sanitizeUrl(m[1]);
|
|
801
|
+
if (!safe) continue;
|
|
802
|
+
out.push(m[2] ? `${safe}${m[2]}` : safe);
|
|
803
|
+
}
|
|
804
|
+
return out.join(", ");
|
|
805
|
+
}
|
|
528
806
|
function sanitizeCSSValue(value) {
|
|
529
|
-
const
|
|
530
|
-
|
|
807
|
+
const decoded = value.replace(/\\([0-9a-fA-F]{1,6})\s?/g, (_m, hex) => {
|
|
808
|
+
const code = Number.parseInt(hex, 16);
|
|
809
|
+
if (!Number.isFinite(code) || code < 0 || code > 1114111) return "";
|
|
810
|
+
try {
|
|
811
|
+
return String.fromCodePoint(code);
|
|
812
|
+
} catch {
|
|
813
|
+
return "";
|
|
814
|
+
}
|
|
815
|
+
});
|
|
816
|
+
const lower = decoded.toLowerCase().replace(/\s+/g, "");
|
|
817
|
+
if (lower.includes("url(") || lower.includes("expression(") || lower.includes("javascript:") || lower.includes("vbscript:") || lower.includes("-moz-binding") || lower.includes("behavior:") || lower.includes("@import") || lower.includes("image-set(") || lower.includes("filter:progid")) {
|
|
531
818
|
return "";
|
|
532
819
|
}
|
|
533
820
|
return value;
|
|
534
821
|
}
|
|
535
|
-
var URL_ATTRIBUTES = /* @__PURE__ */ new Set([
|
|
822
|
+
var URL_ATTRIBUTES = /* @__PURE__ */ new Set([
|
|
823
|
+
"href",
|
|
824
|
+
"xlink:href",
|
|
825
|
+
"src",
|
|
826
|
+
"action",
|
|
827
|
+
"formaction",
|
|
828
|
+
"formtarget",
|
|
829
|
+
"cite",
|
|
830
|
+
"poster",
|
|
831
|
+
"background",
|
|
832
|
+
"srcset",
|
|
833
|
+
"ping",
|
|
834
|
+
"data"
|
|
835
|
+
]);
|
|
536
836
|
function isUrlAttribute(attr) {
|
|
537
837
|
return URL_ATTRIBUTES.has(attr);
|
|
538
838
|
}
|
|
539
839
|
|
|
540
840
|
// src/reactivity/bindAttribute.ts
|
|
541
841
|
var _isDev4 = isDev();
|
|
842
|
+
function setProp(el, key, val) {
|
|
843
|
+
el[key] = val;
|
|
844
|
+
}
|
|
542
845
|
function isEventHandlerAttr(name) {
|
|
543
846
|
if (name.length < 3) return false;
|
|
544
847
|
const lower = name.toLowerCase();
|
|
@@ -564,7 +867,7 @@ function bindAttribute(el, attr, getter) {
|
|
|
564
867
|
}
|
|
565
868
|
if (typeof value === "boolean") {
|
|
566
869
|
if (attr in el && (attr === "checked" || attr === "disabled" || attr === "selected")) {
|
|
567
|
-
el
|
|
870
|
+
setProp(el, attr, value);
|
|
568
871
|
} else if (value) {
|
|
569
872
|
el.setAttribute(attr, "");
|
|
570
873
|
} else {
|
|
@@ -574,7 +877,7 @@ function bindAttribute(el, attr, getter) {
|
|
|
574
877
|
}
|
|
575
878
|
const str = String(value);
|
|
576
879
|
if ((attr === "value" || attr === "checked") && attr in el) {
|
|
577
|
-
el
|
|
880
|
+
setProp(el, attr, attr === "checked" ? Boolean(value) : str);
|
|
578
881
|
} else {
|
|
579
882
|
el.setAttribute(attr, isUrlAttribute(attr) ? sanitizeUrl(str) : str);
|
|
580
883
|
}
|
|
@@ -611,24 +914,29 @@ function bindChildNode(placeholder, getter) {
|
|
|
611
914
|
let newNodes;
|
|
612
915
|
if (Array.isArray(result)) {
|
|
613
916
|
newNodes = [];
|
|
917
|
+
const seen = /* @__PURE__ */ new Set();
|
|
614
918
|
for (let i = 0; i < result.length; i++) {
|
|
615
919
|
const item = result[i];
|
|
616
920
|
if (item == null || typeof item === "boolean") continue;
|
|
617
|
-
|
|
921
|
+
const node = item instanceof Node ? item : document.createTextNode(String(item));
|
|
922
|
+
if (seen.has(node)) {
|
|
923
|
+
if (_isDev5)
|
|
924
|
+
devWarn("bindChildNode: duplicate node reference in array \u2014 only the first occurrence is rendered.");
|
|
925
|
+
continue;
|
|
926
|
+
}
|
|
927
|
+
seen.add(node);
|
|
928
|
+
newNodes.push(node);
|
|
618
929
|
}
|
|
619
930
|
} else {
|
|
620
931
|
const node = result instanceof Node ? result : document.createTextNode(String(result));
|
|
621
932
|
newNodes = [node];
|
|
622
933
|
}
|
|
623
|
-
|
|
624
|
-
if (
|
|
934
|
+
let reused;
|
|
935
|
+
if (lastNodes.length > 0 && newNodes.length > 0) {
|
|
936
|
+
const lastSet = new Set(lastNodes);
|
|
937
|
+
reused = /* @__PURE__ */ new Set();
|
|
625
938
|
for (let i = 0; i < newNodes.length; i++) {
|
|
626
|
-
|
|
627
|
-
if (newNodes[i] === lastNodes[j]) {
|
|
628
|
-
reused.add(newNodes[i]);
|
|
629
|
-
break;
|
|
630
|
-
}
|
|
631
|
-
}
|
|
939
|
+
if (lastSet.has(newNodes[i])) reused.add(newNodes[i]);
|
|
632
940
|
}
|
|
633
941
|
}
|
|
634
942
|
for (let i = 0; i < lastNodes.length; i++) {
|
|
@@ -667,6 +975,30 @@ function registerDisposer(node, teardown) {
|
|
|
667
975
|
}
|
|
668
976
|
|
|
669
977
|
// src/core/rendering/tagFactory.ts
|
|
978
|
+
var _isDev7 = isDev();
|
|
979
|
+
var BLOCKED_TAGS = /* @__PURE__ */ new Set(["script", "iframe", "object", "embed", "frame", "frameset"]);
|
|
980
|
+
function validateTagName(tag) {
|
|
981
|
+
const lower = tag.toLowerCase();
|
|
982
|
+
if (BLOCKED_TAGS.has(lower)) {
|
|
983
|
+
throw new Error(`tagFactory: refusing to create <${tag}> \u2014 tag is blocked for security reasons.`);
|
|
984
|
+
}
|
|
985
|
+
}
|
|
986
|
+
var CLOBBER_RISKY_IDS = /* @__PURE__ */ new Set([
|
|
987
|
+
"config",
|
|
988
|
+
"location",
|
|
989
|
+
"history",
|
|
990
|
+
"document",
|
|
991
|
+
"window",
|
|
992
|
+
"navigator",
|
|
993
|
+
"name",
|
|
994
|
+
"top",
|
|
995
|
+
"parent",
|
|
996
|
+
"self",
|
|
997
|
+
"frames"
|
|
998
|
+
]);
|
|
999
|
+
function setProp2(el, key, val) {
|
|
1000
|
+
el[key] = val;
|
|
1001
|
+
}
|
|
670
1002
|
var kebabCache = /* @__PURE__ */ new Map();
|
|
671
1003
|
function toKebab(prop) {
|
|
672
1004
|
let cached = kebabCache.get(prop);
|
|
@@ -791,79 +1123,103 @@ function appendChildren(el, nodes) {
|
|
|
791
1123
|
}
|
|
792
1124
|
}
|
|
793
1125
|
}
|
|
794
|
-
var tagFactory = (tag, ns) =>
|
|
795
|
-
|
|
796
|
-
|
|
797
|
-
|
|
798
|
-
if (
|
|
799
|
-
|
|
800
|
-
|
|
1126
|
+
var tagFactory = (tag, ns) => {
|
|
1127
|
+
return (first, second) => {
|
|
1128
|
+
validateTagName(tag);
|
|
1129
|
+
const el = ns ? document.createElementNS(ns, tag) : document.createElement(tag);
|
|
1130
|
+
if (first === void 0) return el;
|
|
1131
|
+
if (typeof first === "string") {
|
|
1132
|
+
if (second !== void 0) {
|
|
1133
|
+
el.setAttribute("class", first);
|
|
1134
|
+
appendChildren(el, second);
|
|
1135
|
+
return el;
|
|
1136
|
+
}
|
|
1137
|
+
el.textContent = first;
|
|
801
1138
|
return el;
|
|
802
1139
|
}
|
|
803
|
-
|
|
804
|
-
|
|
805
|
-
|
|
806
|
-
if (typeof first === "number") {
|
|
807
|
-
el.textContent = String(first);
|
|
808
|
-
return el;
|
|
809
|
-
}
|
|
810
|
-
if (Array.isArray(first) || first instanceof Node || typeof first === "function") {
|
|
811
|
-
appendChildren(el, first);
|
|
812
|
-
return el;
|
|
813
|
-
}
|
|
814
|
-
const props = first;
|
|
815
|
-
const pClass = props.class;
|
|
816
|
-
if (pClass != null) applyClass(el, pClass);
|
|
817
|
-
const pId = props.id;
|
|
818
|
-
if (pId != null) el.id = pId;
|
|
819
|
-
const pNodes = second !== void 0 ? second : props.nodes;
|
|
820
|
-
if (pNodes != null) appendChildren(el, pNodes);
|
|
821
|
-
const pOn = props.on;
|
|
822
|
-
if (pOn) {
|
|
823
|
-
for (const ev in pOn) {
|
|
824
|
-
el.addEventListener(ev, pOn[ev]);
|
|
1140
|
+
if (typeof first === "number") {
|
|
1141
|
+
el.textContent = String(first);
|
|
1142
|
+
return el;
|
|
825
1143
|
}
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
843
|
-
|
|
844
|
-
|
|
845
|
-
|
|
846
|
-
|
|
847
|
-
|
|
848
|
-
|
|
849
|
-
|
|
850
|
-
|
|
851
|
-
|
|
852
|
-
|
|
1144
|
+
if (Array.isArray(first) || first instanceof Node || typeof first === "function") {
|
|
1145
|
+
appendChildren(el, first);
|
|
1146
|
+
return el;
|
|
1147
|
+
}
|
|
1148
|
+
const props = first;
|
|
1149
|
+
const pClass = props.class;
|
|
1150
|
+
if (pClass != null) applyClass(el, pClass);
|
|
1151
|
+
const pId = props.id;
|
|
1152
|
+
if (pId != null) {
|
|
1153
|
+
if (_isDev7 && typeof pId === "string" && CLOBBER_RISKY_IDS.has(pId.toLowerCase())) {
|
|
1154
|
+
devWarn(
|
|
1155
|
+
`tagFactory: element id="${pId}" matches a common global and may cause DOM clobbering. Avoid setting ids from untrusted input.`
|
|
1156
|
+
);
|
|
1157
|
+
}
|
|
1158
|
+
el.id = pId;
|
|
1159
|
+
}
|
|
1160
|
+
const pNodes = second !== void 0 ? second : props.nodes;
|
|
1161
|
+
if (pNodes != null) appendChildren(el, pNodes);
|
|
1162
|
+
const pOn = props.on;
|
|
1163
|
+
if (pOn) {
|
|
1164
|
+
for (const ev in pOn) {
|
|
1165
|
+
const handler = pOn[ev];
|
|
1166
|
+
if (typeof handler === "function") {
|
|
1167
|
+
el.addEventListener(ev, handler);
|
|
1168
|
+
} else if (_isDev7) {
|
|
1169
|
+
devWarn(
|
|
1170
|
+
`tagFactory: on.${ev} handler is not a function (got ${typeof handler}). Event listener was not attached.`
|
|
1171
|
+
);
|
|
1172
|
+
}
|
|
1173
|
+
}
|
|
1174
|
+
}
|
|
1175
|
+
const pStyle = props.style;
|
|
1176
|
+
if (pStyle != null) applyStyle(el, pStyle);
|
|
1177
|
+
const pRef = props.ref;
|
|
1178
|
+
if (pRef) pRef.current = el;
|
|
1179
|
+
for (const key in props) {
|
|
1180
|
+
switch (key) {
|
|
1181
|
+
case "class":
|
|
1182
|
+
case "id":
|
|
1183
|
+
case "nodes":
|
|
1184
|
+
case "on":
|
|
1185
|
+
case "style":
|
|
1186
|
+
case "ref":
|
|
1187
|
+
case "onElement":
|
|
1188
|
+
continue;
|
|
1189
|
+
// already handled above / below
|
|
1190
|
+
default: {
|
|
1191
|
+
const value = props[key];
|
|
1192
|
+
if (value == null) continue;
|
|
1193
|
+
const lkey = key.toLowerCase();
|
|
1194
|
+
if (lkey[0] === "o" && lkey[1] === "n") continue;
|
|
1195
|
+
if (typeof value === "function") {
|
|
1196
|
+
registerDisposer(el, bindAttribute(el, key, value));
|
|
1197
|
+
} else if (typeof value === "boolean") {
|
|
1198
|
+
if (key in el && (key === "checked" || key === "disabled" || key === "selected")) {
|
|
1199
|
+
setProp2(el, key, value);
|
|
1200
|
+
} else if (value) {
|
|
1201
|
+
el.setAttribute(key, "");
|
|
1202
|
+
} else {
|
|
1203
|
+
el.removeAttribute(key);
|
|
1204
|
+
}
|
|
853
1205
|
} else {
|
|
854
|
-
|
|
1206
|
+
const str = String(value);
|
|
1207
|
+
if (lkey === "srcset") {
|
|
1208
|
+
el.setAttribute(key, sanitizeSrcset(str));
|
|
1209
|
+
} else if (isUrlAttribute(lkey)) {
|
|
1210
|
+
el.setAttribute(key, sanitizeUrl(str));
|
|
1211
|
+
} else {
|
|
1212
|
+
el.setAttribute(key, str);
|
|
1213
|
+
}
|
|
855
1214
|
}
|
|
856
|
-
} else {
|
|
857
|
-
const str = String(value);
|
|
858
|
-
el.setAttribute(key, isUrlAttribute(key) ? sanitizeUrl(str) : str);
|
|
859
1215
|
}
|
|
860
1216
|
}
|
|
861
1217
|
}
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
1218
|
+
if (props.onElement && typeof props.onElement === "function") {
|
|
1219
|
+
props.onElement(el);
|
|
1220
|
+
}
|
|
1221
|
+
return el;
|
|
1222
|
+
};
|
|
867
1223
|
};
|
|
868
1224
|
|
|
869
1225
|
// src/ecosystem/ui/componentAdapter.ts
|