tutuca 0.10.0 → 0.11.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 +14 -14
- package/dist/immer.js +1261 -0
- package/dist/tutuca-cli.js +1603 -4573
- package/dist/tutuca-components.js +194 -424
- package/dist/tutuca-dev.ext.js +483 -757
- package/dist/tutuca-dev.js +1172 -4999
- package/dist/tutuca-dev.min.js +3 -3
- package/dist/tutuca-extra.ext.js +460 -547
- package/dist/tutuca-extra.js +1136 -4790
- package/dist/tutuca-extra.min.js +2 -2
- package/dist/tutuca-storybook.js +152 -143
- package/dist/tutuca.ext.js +460 -547
- package/dist/tutuca.js +1136 -4790
- package/dist/tutuca.min.js +2 -2
- package/package.json +7 -11
- package/skill/tutuca/SKILL.md +0 -4
- package/skill/tutuca/advanced.md +12 -4
- package/skill/tutuca/cli.md +8 -9
- package/skill/tutuca/component-design.md +18 -19
- package/skill/tutuca/core.md +83 -81
- package/skill/tutuca/iteration.md +2 -2
- package/skill/tutuca/macros.md +1 -1
- package/skill/tutuca/messages-and-intents.md +24 -23
- package/skill/tutuca/patterns/bind-text-and-attributes.md +1 -1
- package/skill/tutuca/patterns/conditional-attribute-value.md +1 -1
- package/skill/tutuca/patterns/coordinate-components.md +10 -8
- package/skill/tutuca/patterns/file-input.md +6 -6
- package/skill/tutuca/patterns/filter-and-paginate.md +1 -1
- package/skill/tutuca/patterns/handle-events.md +10 -8
- package/skill/tutuca/patterns/switch-between-views.md +1 -1
- package/skill/tutuca/patterns/tabbed-interface.md +10 -5
- package/skill/tutuca/testing.md +37 -28
- package/skill/tutuca-source/tutuca.ext.js +460 -547
- package/dist/immutable.js +0 -4331
- package/skill/immutable-js/SKILL.md +0 -78
- package/skill/immutable-js/references/collection.md +0 -346
- package/skill/immutable-js/references/conversions.md +0 -99
- package/skill/immutable-js/references/deep-updates.md +0 -172
- package/skill/immutable-js/references/equality.md +0 -95
- package/skill/immutable-js/references/list.md +0 -266
- package/skill/immutable-js/references/map.md +0 -300
- package/skill/immutable-js/references/predicates.md +0 -93
- package/skill/immutable-js/references/range-repeat.md +0 -55
- package/skill/immutable-js/references/record.md +0 -196
- package/skill/immutable-js/references/seq.md +0 -248
- package/skill/immutable-js/references/set.md +0 -270
- package/skill/immutable-js/references/shallow-functional.md +0 -99
- package/skill/immutable-js/references/stack.md +0 -210
package/dist/tutuca-dev.ext.js
CHANGED
|
@@ -170,11 +170,69 @@ __reExport(chai_exports, chai_star);
|
|
|
170
170
|
import * as chai_star from "chai";
|
|
171
171
|
chai.use(jestMatchers);
|
|
172
172
|
|
|
173
|
-
// src/
|
|
174
|
-
|
|
173
|
+
// src/collection.js
|
|
174
|
+
var isPlainObject = (value) => {
|
|
175
|
+
if (value === null || typeof value !== "object") return false;
|
|
176
|
+
const proto = Object.getPrototypeOf(value);
|
|
177
|
+
return proto === Object.prototype || proto === null;
|
|
178
|
+
};
|
|
179
|
+
var seqSize = (seq) => {
|
|
180
|
+
if (seq == null) return 0;
|
|
181
|
+
if (typeof seq.length === "number") return seq.length;
|
|
182
|
+
if (typeof seq.size === "number") return seq.size;
|
|
183
|
+
return isPlainObject(seq) ? Object.keys(seq).length : 0;
|
|
184
|
+
};
|
|
185
|
+
var seqGet = (seq, key, dval = null) => {
|
|
186
|
+
if (seq == null) return dval;
|
|
187
|
+
if (seq instanceof Map) return seq.has(key) ? seq.get(key) : dval;
|
|
188
|
+
if (seq instanceof Set) return seq.has(key) ? key : dval;
|
|
189
|
+
if (Object.hasOwn(seq, key)) return seq[key];
|
|
190
|
+
if (typeof seq.get === "function") return seq.get(key, dval);
|
|
191
|
+
return dval;
|
|
192
|
+
};
|
|
193
|
+
var isIndexedSeq = (seq) => Array.isArray(seq);
|
|
194
|
+
var isKeyedSeq = (seq) => seq instanceof Map || isPlainObject(seq);
|
|
195
|
+
var isSetSeq = (seq) => seq instanceof Set;
|
|
196
|
+
function* seqEntries(seq) {
|
|
197
|
+
if (seq instanceof Map) yield* seq.entries();
|
|
198
|
+
else if (seq instanceof Set) for (const value of seq) yield [value, value];
|
|
199
|
+
else if (isPlainObject(seq)) yield* Object.entries(seq);
|
|
200
|
+
else if (Array.isArray(seq)) for (let i = 0; i < seq.length; i++) yield [i, seq[i]];
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
// src/immer.js
|
|
204
|
+
var immer_exports = {};
|
|
205
|
+
__reExport(immer_exports, immer_star);
|
|
206
|
+
import { enableMapSet } from "immer";
|
|
207
|
+
import * as immer_star from "immer";
|
|
208
|
+
enableMapSet();
|
|
175
209
|
|
|
176
210
|
// src/path.js
|
|
177
211
|
var NONE = /* @__PURE__ */ Symbol("NONE");
|
|
212
|
+
var readKey = (value, key, dval = null) => {
|
|
213
|
+
if (value == null) return dval;
|
|
214
|
+
if (value instanceof Map) return value.has(key) ? value.get(key) : dval;
|
|
215
|
+
if (value instanceof Set) return value.has(key) ? key : dval;
|
|
216
|
+
return Object.hasOwn(value, key) ? value[key] : dval;
|
|
217
|
+
};
|
|
218
|
+
var writeKey = (value, key, next) => {
|
|
219
|
+
if (value instanceof Map) value.set(key, next);
|
|
220
|
+
else if (value instanceof Set) {
|
|
221
|
+
value.delete(key);
|
|
222
|
+
value.add(next);
|
|
223
|
+
} else value[key] = next;
|
|
224
|
+
};
|
|
225
|
+
var readSeqKey = (value, key, dval = null) => {
|
|
226
|
+
const direct = readKey(value, key, NONE);
|
|
227
|
+
if (direct !== NONE) return direct;
|
|
228
|
+
return typeof value?.get === "function" ? value.get(key, dval) : dval;
|
|
229
|
+
};
|
|
230
|
+
var writeSeqKey = (value, key, next) => {
|
|
231
|
+
if (value instanceof Map || value instanceof Set || Array.isArray(value) || Object.hasOwn(value, key))
|
|
232
|
+
writeKey(value, key, next);
|
|
233
|
+
else if (typeof value?.set === "function") value.set(key, next);
|
|
234
|
+
else writeKey(value, key, next);
|
|
235
|
+
};
|
|
178
236
|
var Step = class {
|
|
179
237
|
lookup(_v, dval = null) {
|
|
180
238
|
return dval;
|
|
@@ -182,6 +240,8 @@ var Step = class {
|
|
|
182
240
|
setValue(root, _v) {
|
|
183
241
|
return root;
|
|
184
242
|
}
|
|
243
|
+
setDraftValue(_root, _v) {
|
|
244
|
+
}
|
|
185
245
|
enterFrame(stack, _prev, next) {
|
|
186
246
|
return stack.enter(next, {}, true);
|
|
187
247
|
}
|
|
@@ -246,10 +306,13 @@ var FieldStep = class extends Step {
|
|
|
246
306
|
this.field = field;
|
|
247
307
|
}
|
|
248
308
|
lookup(v, dval = null) {
|
|
249
|
-
return v
|
|
309
|
+
return readKey(v, this.field, dval);
|
|
250
310
|
}
|
|
251
311
|
setValue(root, v) {
|
|
252
|
-
return
|
|
312
|
+
return (0, immer_exports.produce)(root, (draft) => this.setDraftValue(draft, v));
|
|
313
|
+
}
|
|
314
|
+
setDraftValue(root, v) {
|
|
315
|
+
writeKey(root, this.field, v);
|
|
253
316
|
}
|
|
254
317
|
withIndex(i) {
|
|
255
318
|
return new SeqStep(this.field, i);
|
|
@@ -268,12 +331,14 @@ var SeqStep = class extends Step {
|
|
|
268
331
|
this.key = key;
|
|
269
332
|
}
|
|
270
333
|
lookup(v, dval = null) {
|
|
271
|
-
|
|
272
|
-
return o?.get ? o.get(this.key, dval) : dval;
|
|
334
|
+
return readSeqKey(readKey(v, this.field, null), this.key, dval);
|
|
273
335
|
}
|
|
274
336
|
setValue(root, v) {
|
|
275
|
-
|
|
276
|
-
|
|
337
|
+
return (0, immer_exports.produce)(root, (draft) => this.setDraftValue(draft, v));
|
|
338
|
+
}
|
|
339
|
+
setDraftValue(root, v) {
|
|
340
|
+
const seq = readKey(root, this.field, null);
|
|
341
|
+
if (seq != null) writeSeqKey(seq, this.key, v);
|
|
277
342
|
}
|
|
278
343
|
enterFrame(stack, _prev, next) {
|
|
279
344
|
return stack.enter(next, { key: this.key }, true);
|
|
@@ -289,19 +354,22 @@ var SeqAccessStep = class extends Step {
|
|
|
289
354
|
this.keyField = keyField;
|
|
290
355
|
}
|
|
291
356
|
lookup(v, dval = null) {
|
|
292
|
-
const seq = v
|
|
293
|
-
const key = v
|
|
294
|
-
return key !== NONE && seq
|
|
357
|
+
const seq = readKey(v, this.seqField, NONE);
|
|
358
|
+
const key = readKey(v, this.keyField, NONE);
|
|
359
|
+
return key !== NONE && seq !== NONE ? readSeqKey(seq, key, dval) : dval;
|
|
295
360
|
}
|
|
296
361
|
setValue(root, v) {
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
362
|
+
return (0, immer_exports.produce)(root, (draft) => this.setDraftValue(draft, v));
|
|
363
|
+
}
|
|
364
|
+
setDraftValue(root, v) {
|
|
365
|
+
const seq = readKey(root, this.seqField, NONE);
|
|
366
|
+
const key = readKey(root, this.keyField, NONE);
|
|
367
|
+
if (seq !== NONE && key !== NONE) writeSeqKey(seq, key, v);
|
|
300
368
|
}
|
|
301
369
|
// Resolve `keyField` against `v` now and freeze it as a literal-key `SeqStep`, so a
|
|
302
370
|
// later lookup/setValue lands on this same item even if `keyField` changes meanwhile.
|
|
303
371
|
pinKey(v) {
|
|
304
|
-
const key = v
|
|
372
|
+
const key = readKey(v, this.keyField, NONE);
|
|
305
373
|
return key === NONE ? this : new SeqStep(this.seqField, key);
|
|
306
374
|
}
|
|
307
375
|
// The key is a *field reference* resolved live, so it is unknown without a value;
|
|
@@ -482,19 +550,15 @@ var Path = class _Path {
|
|
|
482
550
|
return out;
|
|
483
551
|
}
|
|
484
552
|
setValue(root, v) {
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
494
|
-
newVal = this.steps[i].setValue(intermediates[i], newVal);
|
|
495
|
-
intermediates[i] = newVal;
|
|
496
|
-
}
|
|
497
|
-
return newVal;
|
|
553
|
+
if (this.steps.length === 0) return v;
|
|
554
|
+
return (0, immer_exports.produce)(root, (draft) => {
|
|
555
|
+
let parent = draft;
|
|
556
|
+
for (let i = 0; i < this.steps.length - 1; i++) {
|
|
557
|
+
parent = this.steps[i].lookup(parent, NONE);
|
|
558
|
+
if (parent === NONE) return;
|
|
559
|
+
}
|
|
560
|
+
this.steps.at(-1).setDraftValue(parent, v);
|
|
561
|
+
});
|
|
498
562
|
}
|
|
499
563
|
buildStack(stack) {
|
|
500
564
|
let prev = stack.it;
|
|
@@ -691,7 +755,8 @@ function sizeOf(v) {
|
|
|
691
755
|
const s = v.size;
|
|
692
756
|
if (typeof s === "number") return s;
|
|
693
757
|
const l = v.length;
|
|
694
|
-
|
|
758
|
+
if (typeof l === "number") return l;
|
|
759
|
+
return isPlainObject(v) ? Object.keys(v).length : null;
|
|
695
760
|
}
|
|
696
761
|
var predTruthy = (v) => {
|
|
697
762
|
const n = sizeOf(v);
|
|
@@ -702,7 +767,7 @@ var PREDICATES = {
|
|
|
702
767
|
"truthy?": { name: "truthy?", arity: 1, fn: predTruthy },
|
|
703
768
|
"falsy?": { name: "falsy?", arity: 1, fn: (v) => !predTruthy(v) },
|
|
704
769
|
"null?": { name: "null?", arity: 1, fn: (v) => v == null },
|
|
705
|
-
"equals?": { name: "equals?", arity: 2, fn: (a, b) => is(a, b) }
|
|
770
|
+
"equals?": { name: "equals?", arity: 2, fn: (a, b) => Object.is(a, b) }
|
|
706
771
|
};
|
|
707
772
|
function parseToken(s, px) {
|
|
708
773
|
const c0 = s.charCodeAt(0);
|
|
@@ -788,20 +853,28 @@ function parseMacroAttr(s, px) {
|
|
|
788
853
|
return _parseSingle(s, px, G_ALL);
|
|
789
854
|
}
|
|
790
855
|
function parseReceiveHandler(s, px) {
|
|
791
|
-
return _parseHandler(s, px, "receive", true, true);
|
|
856
|
+
return _parseHandler(s, px, "receive", true, true, false);
|
|
792
857
|
}
|
|
793
858
|
function parseAlterHandler(s, px) {
|
|
794
|
-
const r = _parseHandler(s, px, "alter", false, false);
|
|
859
|
+
const r = _parseHandler(s, px, "alter", false, false, true);
|
|
795
860
|
return r === null ? null : r.handlerVal;
|
|
796
861
|
}
|
|
797
|
-
function _parseHandler(s, px, namespace, allowArgs, report) {
|
|
862
|
+
function _parseHandler(s, px, namespace, allowArgs, report, allowMethod) {
|
|
798
863
|
const tokens = tokenizeValue(s.trim());
|
|
799
864
|
const headTok = tokens[0] ?? "";
|
|
800
865
|
const head = headTok === "" ? null : parseToken(headTok, px);
|
|
801
866
|
const hk = kindOf(head);
|
|
802
867
|
let handlerVal;
|
|
803
|
-
if (hk & K_METHOD) handlerVal = head;
|
|
804
|
-
else if (hk &
|
|
868
|
+
if (hk & K_METHOD && allowMethod) handlerVal = head;
|
|
869
|
+
else if (hk & K_METHOD) {
|
|
870
|
+
if (report)
|
|
871
|
+
px.onParseIssue("event-method-handler", {
|
|
872
|
+
name: head.name,
|
|
873
|
+
role: "handler-name",
|
|
874
|
+
value: headTok
|
|
875
|
+
});
|
|
876
|
+
return null;
|
|
877
|
+
} else if (hk & K_NAME) handlerVal = new HandlerNameVal(head.name, namespace);
|
|
805
878
|
else {
|
|
806
879
|
if (report) px.onParseIssue("bad-value", { role: "handler-name", value: headTok });
|
|
807
880
|
return null;
|
|
@@ -1015,7 +1088,7 @@ var BindMemberVal = class extends BindVal {
|
|
|
1015
1088
|
}
|
|
1016
1089
|
eval(stack) {
|
|
1017
1090
|
const v = stack.lookupBind(this.name);
|
|
1018
|
-
return
|
|
1091
|
+
return seqGet(v, this.member, null);
|
|
1019
1092
|
}
|
|
1020
1093
|
toString() {
|
|
1021
1094
|
return `@${this.name}.${this.member}`;
|
|
@@ -1062,7 +1135,7 @@ var SeqAccessVal = class extends RenderVal {
|
|
|
1062
1135
|
}
|
|
1063
1136
|
eval(stack) {
|
|
1064
1137
|
const key = this.keyVal.eval(stack);
|
|
1065
|
-
return this.seqVal.eval(stack)
|
|
1138
|
+
return seqGet(this.seqVal.eval(stack), key, null);
|
|
1066
1139
|
}
|
|
1067
1140
|
toString() {
|
|
1068
1141
|
return `${this.seqVal}[${this.keyVal}]`;
|
|
@@ -1342,9 +1415,6 @@ var IntentHandler = class {
|
|
|
1342
1415
|
}
|
|
1343
1416
|
};
|
|
1344
1417
|
|
|
1345
|
-
// src/renderer.js
|
|
1346
|
-
import { isIndexed, isKeyed } from "immutable";
|
|
1347
|
-
|
|
1348
1418
|
// src/cache.js
|
|
1349
1419
|
var isWeakKey = (k) => k !== null && (typeof k === "object" || typeof k === "function");
|
|
1350
1420
|
var NullDomCache = class {
|
|
@@ -1841,7 +1911,7 @@ var Renderer = class {
|
|
|
1841
1911
|
this.cache.set(cachePath, cacheKey, dom);
|
|
1842
1912
|
}
|
|
1843
1913
|
};
|
|
1844
|
-
if (keys)
|
|
1914
|
+
if (keys) keysIter(seq, renderOne, keys);
|
|
1845
1915
|
else
|
|
1846
1916
|
getSeqInfo(seq)(
|
|
1847
1917
|
seq,
|
|
@@ -1875,7 +1945,7 @@ var Renderer = class {
|
|
|
1875
1945
|
return new VFragment([this._renderMetadata({ $: "Scope", nid }), dom]);
|
|
1876
1946
|
}
|
|
1877
1947
|
};
|
|
1878
|
-
var getSeqInfo = (seq) =>
|
|
1948
|
+
var getSeqInfo = (seq) => isIndexedSeq(seq) ? nativeIndexedIter : isKeyedSeq(seq) || isSetSeq(seq) ? nativeKeyedIter : seq?.[SEQ_INFO] ?? unkIter;
|
|
1879
1949
|
var normalizeRange = (start, end, size) => {
|
|
1880
1950
|
let s = start == null ? 0 : start < 0 ? size + start : start;
|
|
1881
1951
|
let e = end == null ? size : end < 0 ? size + end : end;
|
|
@@ -1898,22 +1968,22 @@ var unpackLoopResult = (result, seq) => {
|
|
|
1898
1968
|
const r = result ?? {};
|
|
1899
1969
|
return { iterData: r.iterData ?? { seq }, start: r.start, end: r.end, keys: r.keys };
|
|
1900
1970
|
};
|
|
1901
|
-
var
|
|
1902
|
-
const attrName =
|
|
1903
|
-
for (const key of keys) visit(key, seq
|
|
1971
|
+
var keysIter = (seq, visit, keys) => {
|
|
1972
|
+
const attrName = isIndexedSeq(seq) ? "si" : "sk";
|
|
1973
|
+
for (const key of keys) visit(key, seqGet(seq, key), attrName);
|
|
1904
1974
|
};
|
|
1905
1975
|
var makeLoopCtx = (stack, filter) => ({
|
|
1906
1976
|
lookup: (name) => stack.lookupBind(name),
|
|
1907
1977
|
filter: (key, value, iterData) => filter.call(stack.it, key, value, iterData)
|
|
1908
1978
|
});
|
|
1909
|
-
var
|
|
1910
|
-
const [s, e] = normalizeRange(start, end, seq
|
|
1911
|
-
for (let i = s; i < e; i++) visit(i, seq
|
|
1979
|
+
var nativeIndexedIter = (seq, visit, start, end) => {
|
|
1980
|
+
const [s, e] = normalizeRange(start, end, seqSize(seq));
|
|
1981
|
+
for (let i = s; i < e; i++) visit(i, seq[i], "si");
|
|
1912
1982
|
};
|
|
1913
|
-
var
|
|
1914
|
-
const [s, e] = normalizeRange(start, end, seq
|
|
1983
|
+
var nativeKeyedIter = (seq, visit, start, end) => {
|
|
1984
|
+
const [s, e] = normalizeRange(start, end, seqSize(seq));
|
|
1915
1985
|
let i = 0;
|
|
1916
|
-
for (const [k, v] of seq
|
|
1986
|
+
for (const [k, v] of seqEntries(seq)) {
|
|
1917
1987
|
if (i >= e) break;
|
|
1918
1988
|
if (i >= s) visit(k, v, "sk");
|
|
1919
1989
|
i++;
|
|
@@ -2433,7 +2503,7 @@ var IterInfo = class {
|
|
|
2433
2503
|
// { key, value }, then run @enrich-with (with @loop-with's iterData) if any.
|
|
2434
2504
|
enrichBinds(stack, key) {
|
|
2435
2505
|
const { seq, filter, loopWith, enricher } = this.eval(stack);
|
|
2436
|
-
const value = seq
|
|
2506
|
+
const value = seqGet(seq, key, null);
|
|
2437
2507
|
const binds = { key, value };
|
|
2438
2508
|
if (enricher) {
|
|
2439
2509
|
const { iterData } = unpackLoopResult(
|
|
@@ -5057,12 +5127,10 @@ var RENDER_IT_OUTSIDE_OF_LOOP = "RENDER_IT_OUTSIDE_OF_LOOP";
|
|
|
5057
5127
|
var UNKNOWN_EVENT_MODIFIER = "UNKNOWN_EVENT_MODIFIER";
|
|
5058
5128
|
var UNKNOWN_HANDLER_ARG_NAME = "UNKNOWN_HANDLER_ARG_NAME";
|
|
5059
5129
|
var RECEIVE_HANDLER_NOT_IMPLEMENTED = "RECEIVE_HANDLER_NOT_IMPLEMENTED";
|
|
5130
|
+
var EVENT_HANDLER_METHOD_NOT_ALLOWED = "EVENT_HANDLER_METHOD_NOT_ALLOWED";
|
|
5060
5131
|
var RETIRED_HANDLER_BUCKET = "RETIRED_HANDLER_BUCKET";
|
|
5061
5132
|
var RETIRED_CTX_VERB = "RETIRED_CTX_VERB";
|
|
5062
5133
|
var HANDLER_NAME_COLLISION = "HANDLER_NAME_COLLISION";
|
|
5063
|
-
var RECEIVE_HANDLER_METHOD_NOT_IMPLEMENTED = "RECEIVE_HANDLER_METHOD_NOT_IMPLEMENTED";
|
|
5064
|
-
var RECEIVE_HANDLER_FOR_METHOD = "RECEIVE_HANDLER_FOR_METHOD";
|
|
5065
|
-
var METHOD_FOR_RECEIVE_HANDLER = "METHOD_FOR_RECEIVE_HANDLER";
|
|
5066
5134
|
var FIELD_VAL_NOT_DEFINED = "FIELD_VAL_NOT_DEFINED";
|
|
5067
5135
|
var FIELD_VAL_IS_METHOD = "FIELD_VAL_IS_METHOD";
|
|
5068
5136
|
var METHOD_VAL_NOT_DEFINED = "METHOD_VAL_NOT_DEFINED";
|
|
@@ -5090,8 +5158,7 @@ var COMP_FIELD_BAD_SHAPE = "COMP_FIELD_BAD_SHAPE";
|
|
|
5090
5158
|
var ASYNC_HANDLER = "ASYNC_HANDLER";
|
|
5091
5159
|
var TOP_LEVEL_AT_RULE_IN_SCOPED_STYLE = "TOP_LEVEL_AT_RULE_IN_SCOPED_STYLE";
|
|
5092
5160
|
var GLOBAL_SELECTOR_IN_SCOPED_STYLE = "GLOBAL_SELECTOR_IN_SCOPED_STYLE";
|
|
5093
|
-
var
|
|
5094
|
-
var RECORD_FIELD_NAME_COLLISIONS = /* @__PURE__ */ new Set(["entries", "hashCode"]);
|
|
5161
|
+
var FIELD_METHOD_NAME_COLLISION = "FIELD_METHOD_NAME_COLLISION";
|
|
5095
5162
|
var X_KNOWN_OP_NAMES = /* @__PURE__ */ new Set([
|
|
5096
5163
|
"slot",
|
|
5097
5164
|
"text",
|
|
@@ -5114,7 +5181,8 @@ var PARSE_ISSUES = {
|
|
|
5114
5181
|
candidates: X_KNOWN_ATTR_NAMES,
|
|
5115
5182
|
atPrefix: X_KNOWN_ATTR_NAMES
|
|
5116
5183
|
},
|
|
5117
|
-
"bad-value": { id: BAD_VALUE }
|
|
5184
|
+
"bad-value": { id: BAD_VALUE },
|
|
5185
|
+
"event-method-handler": { id: EVENT_HANDLER_METHOD_NOT_ALLOWED }
|
|
5118
5186
|
};
|
|
5119
5187
|
function protoHasMethod(proto, name) {
|
|
5120
5188
|
return protoMethodValue(proto, name) !== null;
|
|
@@ -5176,7 +5244,7 @@ function checkComponent(Comp, lx = new LintContext(), { wellKnownExtras = EMPTY_
|
|
|
5176
5244
|
return lx.push({ componentName: Comp.name }, () => {
|
|
5177
5245
|
checkUnknownSpecKeys(lx, Comp, wellKnownExtras);
|
|
5178
5246
|
checkFieldDeclarations(lx, Comp);
|
|
5179
|
-
|
|
5247
|
+
checkFieldMethodNameCollisions(lx, Comp);
|
|
5180
5248
|
checkProvidesAreAddressable(lx, Comp);
|
|
5181
5249
|
checkLookupShapes(lx, Comp);
|
|
5182
5250
|
checkHandlersNotAsync(lx, Comp);
|
|
@@ -5239,6 +5307,14 @@ function checkParseIssues(lx, view) {
|
|
|
5239
5307
|
lx.warn(X_OP_IGNORES_CHILDREN, info, { kind: "remove", what: "the ignored children" });
|
|
5240
5308
|
continue;
|
|
5241
5309
|
}
|
|
5310
|
+
if (kind === "event-method-handler") {
|
|
5311
|
+
lx.error(EVENT_HANDLER_METHOD_NOT_ALLOWED, info, {
|
|
5312
|
+
kind: "rephrase",
|
|
5313
|
+
from: info.value,
|
|
5314
|
+
text: `Move '${info.name}' to receive and reference it as '${info.name}'.`
|
|
5315
|
+
});
|
|
5316
|
+
continue;
|
|
5317
|
+
}
|
|
5242
5318
|
const rule = PARSE_ISSUES[kind];
|
|
5243
5319
|
if (!rule) continue;
|
|
5244
5320
|
const id = rule.id;
|
|
@@ -5473,44 +5549,22 @@ function checkEventHandlersHaveImpls(lx, Comp, referencedInputs) {
|
|
|
5473
5549
|
for (const event of view.ctx.events) {
|
|
5474
5550
|
for (const handler of event.handlers) {
|
|
5475
5551
|
const { handlerVal } = handler.handlerCall;
|
|
5476
|
-
const hvName = handlerVal?.constructor.name;
|
|
5477
5552
|
const eventName = handler.name;
|
|
5478
5553
|
const originAttr = `@on.${eventName}`;
|
|
5479
|
-
if (
|
|
5554
|
+
if (handlerVal?.constructor.name === "HandlerNameVal") {
|
|
5480
5555
|
referencedInputs?.add(handlerVal.name);
|
|
5481
5556
|
const { name } = handlerVal;
|
|
5482
5557
|
if (input[name] === void 0) {
|
|
5483
|
-
const
|
|
5558
|
+
const suggestion = protoHasMethod(proto, name) ? {
|
|
5559
|
+
kind: "rephrase",
|
|
5560
|
+
from: name,
|
|
5561
|
+
text: `Move '${name}' from methods to receive; event handlers are receive handlers.`
|
|
5562
|
+
} : replaceNameSuggestion(name, Object.keys(input));
|
|
5484
5563
|
lx.error(
|
|
5485
5564
|
RECEIVE_HANDLER_NOT_IMPLEMENTED,
|
|
5486
5565
|
{ name, handler, event, eventName, originAttr },
|
|
5487
|
-
|
|
5488
|
-
);
|
|
5489
|
-
if (isMethodFix) {
|
|
5490
|
-
lx.hint(
|
|
5491
|
-
METHOD_FOR_RECEIVE_HANDLER,
|
|
5492
|
-
{ name, handler, event, eventName, originAttr },
|
|
5493
|
-
{ kind: "add-prefix", from: name, to: `$${name}` }
|
|
5494
|
-
);
|
|
5495
|
-
}
|
|
5496
|
-
}
|
|
5497
|
-
} else if (hvName === "MethodVal") {
|
|
5498
|
-
referencedInputs?.add(handlerVal.name);
|
|
5499
|
-
const { name } = handlerVal;
|
|
5500
|
-
if (!protoHasMethod(proto, name)) {
|
|
5501
|
-
const isInputFix = input[name] !== void 0;
|
|
5502
|
-
lx.error(
|
|
5503
|
-
RECEIVE_HANDLER_METHOD_NOT_IMPLEMENTED,
|
|
5504
|
-
{ name, handler, event, eventName, originAttr },
|
|
5505
|
-
isInputFix ? { kind: "drop-prefix", from: `$${name}`, to: name } : replaceNameSuggestion(name, collectProtoMethodNames(proto))
|
|
5566
|
+
suggestion
|
|
5506
5567
|
);
|
|
5507
|
-
if (isInputFix) {
|
|
5508
|
-
lx.hint(
|
|
5509
|
-
RECEIVE_HANDLER_FOR_METHOD,
|
|
5510
|
-
{ name, handler, event, eventName, originAttr },
|
|
5511
|
-
{ kind: "drop-prefix", from: `$${name}`, to: name }
|
|
5512
|
-
);
|
|
5513
|
-
}
|
|
5514
5568
|
}
|
|
5515
5569
|
}
|
|
5516
5570
|
}
|
|
@@ -5614,10 +5668,10 @@ var ATTR_VAL_CHECKERS = {
|
|
|
5614
5668
|
}
|
|
5615
5669
|
};
|
|
5616
5670
|
function checkConsistentAttrVal(lx, val, env, skipNameVal = false, errCtx = null, isRoot = true) {
|
|
5617
|
-
const
|
|
5618
|
-
if (
|
|
5671
|
+
const check3 = ATTR_VAL_CHECKERS[val?.constructor.name];
|
|
5672
|
+
if (check3 === void 0) return;
|
|
5619
5673
|
const recurse = (sub) => checkConsistentAttrVal(lx, sub, env, skipNameVal, errCtx, false);
|
|
5620
|
-
|
|
5674
|
+
check3({ lx, val, env, errCtx, skipNameVal, recurse, isRoot });
|
|
5621
5675
|
}
|
|
5622
5676
|
var NODE_KIND_TO_CTX = {
|
|
5623
5677
|
RenderTextNode: { originAttr: "<x text>" },
|
|
@@ -5863,14 +5917,11 @@ function checkFieldDeclarations(lx, Comp) {
|
|
|
5863
5917
|
}
|
|
5864
5918
|
}
|
|
5865
5919
|
}
|
|
5866
|
-
function
|
|
5867
|
-
const
|
|
5868
|
-
if (!
|
|
5869
|
-
for (const name in fields)
|
|
5870
|
-
if (
|
|
5871
|
-
lx.error(FIELD_NAME_RESERVED_BY_RECORD, { name });
|
|
5872
|
-
}
|
|
5873
|
-
}
|
|
5920
|
+
function checkFieldMethodNameCollisions(lx, Comp) {
|
|
5921
|
+
const meta = Comp.Class?.getMetaClass?.();
|
|
5922
|
+
if (!meta) return;
|
|
5923
|
+
for (const name in meta.fields)
|
|
5924
|
+
if (Object.hasOwn(meta.methods, name)) lx.error(FIELD_METHOD_NAME_COLLISION, { name });
|
|
5874
5925
|
}
|
|
5875
5926
|
function checkUnreferencedAlterHandlers(lx, Comp, referencedAlters) {
|
|
5876
5927
|
for (const name in Comp.alter) {
|
|
@@ -6269,6 +6320,316 @@ function dispatchPhase(dispatcher, targetPath, phase, self) {
|
|
|
6269
6320
|
}
|
|
6270
6321
|
}
|
|
6271
6322
|
|
|
6323
|
+
// src/oo.js
|
|
6324
|
+
var BAD_VALUE2 = /* @__PURE__ */ Symbol("BadValue");
|
|
6325
|
+
var nullCoercer = (v) => v;
|
|
6326
|
+
var isPlainObject2 = (v) => {
|
|
6327
|
+
if (v === null || typeof v !== "object") return false;
|
|
6328
|
+
const proto = Object.getPrototypeOf(v);
|
|
6329
|
+
return proto === Object.prototype || proto === null;
|
|
6330
|
+
};
|
|
6331
|
+
function defaultToData(v) {
|
|
6332
|
+
if (v instanceof Map) return [...v.entries()];
|
|
6333
|
+
if (v instanceof Set) return [...v.values()];
|
|
6334
|
+
return v;
|
|
6335
|
+
}
|
|
6336
|
+
var Field = class {
|
|
6337
|
+
constructor(type, name, typeCheck, coercer, defaultValue = null) {
|
|
6338
|
+
this.type = type;
|
|
6339
|
+
this.name = name;
|
|
6340
|
+
this.typeCheck = typeCheck;
|
|
6341
|
+
this.coercer = coercer;
|
|
6342
|
+
this.checks = [];
|
|
6343
|
+
this.defaultValue = defaultValue;
|
|
6344
|
+
}
|
|
6345
|
+
toDataDef() {
|
|
6346
|
+
return { type: this.type, defaultValue: defaultToData(this.defaultValue) };
|
|
6347
|
+
}
|
|
6348
|
+
getFirstFailingCheck(v) {
|
|
6349
|
+
if (!this.typeCheck.isValid(v)) return this.typeCheck;
|
|
6350
|
+
for (const check3 of this.checks) if (!check3.isValid(v)) return check3;
|
|
6351
|
+
return null;
|
|
6352
|
+
}
|
|
6353
|
+
isValid(v) {
|
|
6354
|
+
return this.getFirstFailingCheck(v) === null;
|
|
6355
|
+
}
|
|
6356
|
+
addCheck(check3) {
|
|
6357
|
+
this.checks.push(check3);
|
|
6358
|
+
return this;
|
|
6359
|
+
}
|
|
6360
|
+
coerceOr(v, defaultValue = null) {
|
|
6361
|
+
if (this.isValid(v)) return v;
|
|
6362
|
+
const v1 = this.coercer(v);
|
|
6363
|
+
return this.isValid(v1) ? v1 : defaultValue;
|
|
6364
|
+
}
|
|
6365
|
+
coerceOrDefault(v) {
|
|
6366
|
+
return this.coerceOr(v, this.defaultValue);
|
|
6367
|
+
}
|
|
6368
|
+
};
|
|
6369
|
+
var Check = class {
|
|
6370
|
+
isValid(_v) {
|
|
6371
|
+
return true;
|
|
6372
|
+
}
|
|
6373
|
+
getMessage(_v) {
|
|
6374
|
+
return "Invalid";
|
|
6375
|
+
}
|
|
6376
|
+
};
|
|
6377
|
+
var CheckTypeAny = class extends Check {
|
|
6378
|
+
};
|
|
6379
|
+
var CHECK_TYPE_ANY = new CheckTypeAny();
|
|
6380
|
+
var FnCheck = class extends Check {
|
|
6381
|
+
constructor(isValidFn, getMessageFn) {
|
|
6382
|
+
super();
|
|
6383
|
+
this._isValid = isValidFn;
|
|
6384
|
+
this._getMessage = getMessageFn;
|
|
6385
|
+
}
|
|
6386
|
+
isValid(v) {
|
|
6387
|
+
return this._isValid(v);
|
|
6388
|
+
}
|
|
6389
|
+
getMessage(v) {
|
|
6390
|
+
return this._getMessage(v);
|
|
6391
|
+
}
|
|
6392
|
+
};
|
|
6393
|
+
var check = (fn, message) => new FnCheck(fn, () => message);
|
|
6394
|
+
var CHECK_TYPE_INT = check(Number.isInteger, "Integer expected");
|
|
6395
|
+
var CHECK_TYPE_FLOAT = check(Number.isFinite, "Float expected");
|
|
6396
|
+
var CHECK_TYPE_BOOL = check((v) => typeof v === "boolean", "Boolean expected");
|
|
6397
|
+
var CHECK_TYPE_STRING = check((v) => typeof v === "string", "String expected");
|
|
6398
|
+
var CHECK_TYPE_LIST = check(Array.isArray, "Array expected");
|
|
6399
|
+
var CHECK_TYPE_OBJECT = check(isPlainObject2, "Plain object expected");
|
|
6400
|
+
var CHECK_TYPE_MAP = check((v) => v instanceof Map, "Map expected");
|
|
6401
|
+
var CHECK_TYPE_SET = check((v) => v instanceof Set, "Set expected");
|
|
6402
|
+
var FieldBool = class extends Field {
|
|
6403
|
+
constructor(name, defaultValue = false) {
|
|
6404
|
+
super("bool", name, CHECK_TYPE_BOOL, (v) => !!v, defaultValue);
|
|
6405
|
+
}
|
|
6406
|
+
};
|
|
6407
|
+
var FieldAny = class extends Field {
|
|
6408
|
+
constructor(name, defaultValue = null) {
|
|
6409
|
+
super("any", name, CHECK_TYPE_ANY, nullCoercer, defaultValue);
|
|
6410
|
+
}
|
|
6411
|
+
toDataDef() {
|
|
6412
|
+
return { type: getTypeName(this.defaultValue) ?? "any", defaultValue: this.defaultValue };
|
|
6413
|
+
}
|
|
6414
|
+
};
|
|
6415
|
+
var FieldString = class extends Field {
|
|
6416
|
+
constructor(name, defaultValue = "") {
|
|
6417
|
+
super("text", name, CHECK_TYPE_STRING, (v) => v?.toString?.() ?? "", defaultValue);
|
|
6418
|
+
}
|
|
6419
|
+
};
|
|
6420
|
+
var FieldInt = class extends Field {
|
|
6421
|
+
constructor(name, defaultValue = 0) {
|
|
6422
|
+
super(
|
|
6423
|
+
"int",
|
|
6424
|
+
name,
|
|
6425
|
+
CHECK_TYPE_INT,
|
|
6426
|
+
(v) => Number.isFinite(v) ? Math.trunc(v) : null,
|
|
6427
|
+
defaultValue
|
|
6428
|
+
);
|
|
6429
|
+
}
|
|
6430
|
+
};
|
|
6431
|
+
var FieldFloat = class extends Field {
|
|
6432
|
+
constructor(name, defaultValue = 0) {
|
|
6433
|
+
super("float", name, CHECK_TYPE_FLOAT, (_) => null, defaultValue);
|
|
6434
|
+
}
|
|
6435
|
+
};
|
|
6436
|
+
var getTypeName = (v) => v?.constructor?.getMetaClass?.()?.name;
|
|
6437
|
+
var CheckTypeName = class {
|
|
6438
|
+
constructor(typeName) {
|
|
6439
|
+
this.typeName = typeName;
|
|
6440
|
+
}
|
|
6441
|
+
isValid(v) {
|
|
6442
|
+
return getTypeName(v) === this.typeName;
|
|
6443
|
+
}
|
|
6444
|
+
getMessage(v) {
|
|
6445
|
+
return `Expected "${this.typeName}", got "${getTypeName(v)}"`;
|
|
6446
|
+
}
|
|
6447
|
+
};
|
|
6448
|
+
var FieldComp = class extends Field {
|
|
6449
|
+
constructor(type, name, args) {
|
|
6450
|
+
super(type, name, new CheckTypeName(type), nullCoercer, null);
|
|
6451
|
+
this.args = args;
|
|
6452
|
+
}
|
|
6453
|
+
toDataDef() {
|
|
6454
|
+
return { component: this.type, args: this.args };
|
|
6455
|
+
}
|
|
6456
|
+
};
|
|
6457
|
+
var FieldList = class extends Field {
|
|
6458
|
+
constructor(name, defaultValue = []) {
|
|
6459
|
+
super("list", name, CHECK_TYPE_LIST, (v) => Array.isArray(v) ? [...v] : null, defaultValue);
|
|
6460
|
+
}
|
|
6461
|
+
};
|
|
6462
|
+
var FieldObject = class extends Field {
|
|
6463
|
+
constructor(name, defaultValue = {}) {
|
|
6464
|
+
super(
|
|
6465
|
+
"object",
|
|
6466
|
+
name,
|
|
6467
|
+
CHECK_TYPE_OBJECT,
|
|
6468
|
+
(v) => isPlainObject2(v) ? { ...v } : null,
|
|
6469
|
+
defaultValue
|
|
6470
|
+
);
|
|
6471
|
+
}
|
|
6472
|
+
};
|
|
6473
|
+
var FieldMap = class extends Field {
|
|
6474
|
+
constructor(name, defaultValue = /* @__PURE__ */ new Map()) {
|
|
6475
|
+
super(
|
|
6476
|
+
"map",
|
|
6477
|
+
name,
|
|
6478
|
+
CHECK_TYPE_MAP,
|
|
6479
|
+
(v) => {
|
|
6480
|
+
if (v instanceof Map) return new Map(v);
|
|
6481
|
+
if (Array.isArray(v) || isPlainObject2(v))
|
|
6482
|
+
return new Map(Array.isArray(v) ? v : Object.entries(v));
|
|
6483
|
+
return null;
|
|
6484
|
+
},
|
|
6485
|
+
defaultValue
|
|
6486
|
+
);
|
|
6487
|
+
}
|
|
6488
|
+
};
|
|
6489
|
+
var FieldSet = class extends Field {
|
|
6490
|
+
constructor(name, defaultValue = /* @__PURE__ */ new Set()) {
|
|
6491
|
+
super(
|
|
6492
|
+
"set",
|
|
6493
|
+
name,
|
|
6494
|
+
CHECK_TYPE_SET,
|
|
6495
|
+
(v) => v instanceof Set || Array.isArray(v) ? new Set(v) : null,
|
|
6496
|
+
defaultValue
|
|
6497
|
+
);
|
|
6498
|
+
}
|
|
6499
|
+
};
|
|
6500
|
+
function mkCompField(field, scope, args) {
|
|
6501
|
+
const Comp = scope?.lookupComponent(field.type) ?? null;
|
|
6502
|
+
if (Comp === null)
|
|
6503
|
+
console.warn(
|
|
6504
|
+
scope ? `component field "${field.name}": component "${field.type}" not found in scope` : `component field "${field.name}": cannot resolve component "${field.type}" — built without a registered scope (use ${field.type}.make({}) as the default, or build via a registered component)`
|
|
6505
|
+
);
|
|
6506
|
+
return Comp?.make({ ...field.args, ...args }, { scope }) ?? null;
|
|
6507
|
+
}
|
|
6508
|
+
var ClassBuilder = class {
|
|
6509
|
+
constructor(name) {
|
|
6510
|
+
this.name = name;
|
|
6511
|
+
this.fields = {};
|
|
6512
|
+
this.compFields = /* @__PURE__ */ new Set();
|
|
6513
|
+
this._methods = {};
|
|
6514
|
+
this._statics = {};
|
|
6515
|
+
}
|
|
6516
|
+
build() {
|
|
6517
|
+
const { name, fields, compFields, _methods } = this;
|
|
6518
|
+
const defaults = Object.fromEntries(
|
|
6519
|
+
Object.entries(fields).map(([fieldName, field]) => [fieldName, field.defaultValue])
|
|
6520
|
+
);
|
|
6521
|
+
const Class = {
|
|
6522
|
+
[name]: class {
|
|
6523
|
+
constructor(values = {}) {
|
|
6524
|
+
Object.assign(this, defaults, values);
|
|
6525
|
+
}
|
|
6526
|
+
}
|
|
6527
|
+
}[name];
|
|
6528
|
+
Class[immer_exports.immerable] = true;
|
|
6529
|
+
Object.assign(Class.prototype, _methods);
|
|
6530
|
+
const metaClass = { fields, name, methods: _methods };
|
|
6531
|
+
Object.assign(
|
|
6532
|
+
Class,
|
|
6533
|
+
{
|
|
6534
|
+
getMetaClass: () => metaClass,
|
|
6535
|
+
make(inArgs = {}, opts = {}) {
|
|
6536
|
+
const args = {};
|
|
6537
|
+
const scope = opts.scope ?? this.scope;
|
|
6538
|
+
for (const key in inArgs) {
|
|
6539
|
+
const field = fields[key];
|
|
6540
|
+
if (compFields.has(key)) args[key] = mkCompField(field, scope, inArgs[key]);
|
|
6541
|
+
else if (field === void 0)
|
|
6542
|
+
console.warn("extra argument to constructor:", name, key, inArgs);
|
|
6543
|
+
else args[key] = field.coerceOrDefault(inArgs[key]);
|
|
6544
|
+
}
|
|
6545
|
+
for (const key of compFields)
|
|
6546
|
+
if (args[key] === void 0) args[key] = mkCompField(fields[key], scope, inArgs[key]);
|
|
6547
|
+
return (0, immer_exports.freeze)(new this(args), true);
|
|
6548
|
+
}
|
|
6549
|
+
},
|
|
6550
|
+
this._statics
|
|
6551
|
+
);
|
|
6552
|
+
return Class;
|
|
6553
|
+
}
|
|
6554
|
+
methods(proto) {
|
|
6555
|
+
for (const k in proto) this._methods[k] = proto[k];
|
|
6556
|
+
}
|
|
6557
|
+
statics(proto) {
|
|
6558
|
+
for (const k in proto) this._statics[k] = proto[k];
|
|
6559
|
+
}
|
|
6560
|
+
addField(name, dval, FieldCls) {
|
|
6561
|
+
const field = new FieldCls(name, dval);
|
|
6562
|
+
this.fields[name] = field;
|
|
6563
|
+
return field;
|
|
6564
|
+
}
|
|
6565
|
+
addCompField(name, type, args) {
|
|
6566
|
+
const field = new FieldComp(type, name, args);
|
|
6567
|
+
this.compFields.add(name);
|
|
6568
|
+
this.fields[name] = field;
|
|
6569
|
+
return field;
|
|
6570
|
+
}
|
|
6571
|
+
};
|
|
6572
|
+
var FIELD_CLASS = /* @__PURE__ */ Symbol.for("tutuca.fieldClass");
|
|
6573
|
+
var fieldsByTypeName = {
|
|
6574
|
+
text: FieldString,
|
|
6575
|
+
int: FieldInt,
|
|
6576
|
+
float: FieldFloat,
|
|
6577
|
+
bool: FieldBool,
|
|
6578
|
+
list: FieldList,
|
|
6579
|
+
object: FieldObject,
|
|
6580
|
+
map: FieldMap,
|
|
6581
|
+
set: FieldSet,
|
|
6582
|
+
any: FieldAny
|
|
6583
|
+
};
|
|
6584
|
+
function fieldFromDescriptor(name, value) {
|
|
6585
|
+
const FieldCls = fieldsByTypeName[value.type] ?? FieldAny;
|
|
6586
|
+
const probe = new FieldCls(name);
|
|
6587
|
+
return [FieldCls, probe.coerceOr(value.defaultValue, probe.defaultValue)];
|
|
6588
|
+
}
|
|
6589
|
+
function classFromData(name, { fields = {}, methods, statics }) {
|
|
6590
|
+
const b = new ClassBuilder(name);
|
|
6591
|
+
for (const field in fields) {
|
|
6592
|
+
const value = fields[field];
|
|
6593
|
+
const type = typeof value;
|
|
6594
|
+
if (type === "string") b.addField(field, value, FieldString);
|
|
6595
|
+
else if (type === "number")
|
|
6596
|
+
b.addField(field, value, Number.isInteger(value) ? FieldInt : FieldFloat);
|
|
6597
|
+
else if (type === "boolean") b.addField(field, value, FieldBool);
|
|
6598
|
+
else if (Array.isArray(value)) b.addField(field, [...value], FieldList);
|
|
6599
|
+
else if (value instanceof Set) b.addField(field, new Set(value), FieldSet);
|
|
6600
|
+
else if (value instanceof Map) b.addField(field, new Map(value), FieldMap);
|
|
6601
|
+
else if (value?.type && Object.hasOwn(value, "defaultValue")) {
|
|
6602
|
+
const [FieldCls, dval] = fieldFromDescriptor(field, value);
|
|
6603
|
+
b.addField(field, dval, FieldCls);
|
|
6604
|
+
} else if (value?.component && value?.args !== void 0)
|
|
6605
|
+
b.addCompField(field, value.component, value.args);
|
|
6606
|
+
else if (isPlainObject2(value)) b.addField(field, { ...value }, FieldObject);
|
|
6607
|
+
else {
|
|
6608
|
+
const FieldCls = value?.[FIELD_CLASS] ?? FieldAny;
|
|
6609
|
+
b.addField(field, value, FieldCls);
|
|
6610
|
+
}
|
|
6611
|
+
}
|
|
6612
|
+
if (methods) b.methods(methods);
|
|
6613
|
+
if (statics) b.statics(statics);
|
|
6614
|
+
return b.build();
|
|
6615
|
+
}
|
|
6616
|
+
function validateDraftFields(current, draft) {
|
|
6617
|
+
const meta = current?.constructor?.getMetaClass?.();
|
|
6618
|
+
if (!meta) return;
|
|
6619
|
+
for (const [name, field] of Object.entries(meta.fields)) {
|
|
6620
|
+
const value = draft[name];
|
|
6621
|
+
if (field.isValid(value)) continue;
|
|
6622
|
+
const coerced = field.coerceOr(value, BAD_VALUE2);
|
|
6623
|
+
if (coerced !== BAD_VALUE2) draft[name] = coerced;
|
|
6624
|
+
else {
|
|
6625
|
+
console.warn(`invalid value for ${meta.name}.${name}`, value);
|
|
6626
|
+
draft[name] = current[name];
|
|
6627
|
+
}
|
|
6628
|
+
}
|
|
6629
|
+
}
|
|
6630
|
+
Component.fromSpec = (opts) => new Component(classFromData(opts.name, opts), opts);
|
|
6631
|
+
var component = (opts) => Component.fromSpec(opts);
|
|
6632
|
+
|
|
6272
6633
|
// src/stack.js
|
|
6273
6634
|
var STOP = /* @__PURE__ */ Symbol("STOP");
|
|
6274
6635
|
var NEXT = /* @__PURE__ */ Symbol("NEXT");
|
|
@@ -6327,12 +6688,12 @@ var Stack = class _Stack {
|
|
|
6327
6688
|
const provide = this.comps.getCompFor(this.it)?.provide;
|
|
6328
6689
|
if (provide == null) return this;
|
|
6329
6690
|
const dynObj = {};
|
|
6330
|
-
let
|
|
6691
|
+
let has = false;
|
|
6331
6692
|
for (const k in provide) {
|
|
6332
6693
|
dynObj[provide[k].symbol] = provide[k].val.eval(this);
|
|
6333
|
-
|
|
6694
|
+
has = true;
|
|
6334
6695
|
}
|
|
6335
|
-
if (!
|
|
6696
|
+
if (!has) return this;
|
|
6336
6697
|
const newDynBinds = [new ObjectFrame(dynObj), this.dynBinds];
|
|
6337
6698
|
const { comps, it, binds, views, viewsId, ctx } = this;
|
|
6338
6699
|
return new _Stack(comps, it, binds, newDynBinds, views, viewsId, ctx);
|
|
@@ -6590,10 +6951,10 @@ var Transaction = class {
|
|
|
6590
6951
|
get observeName() {
|
|
6591
6952
|
return null;
|
|
6592
6953
|
}
|
|
6593
|
-
callHandler(root, instance, comps) {
|
|
6954
|
+
callHandler(root, instance, draft, comps) {
|
|
6594
6955
|
const [handler, args] = this.getHandlerAndArgs(root, instance, comps);
|
|
6595
6956
|
this._resolvedHandler = handler;
|
|
6596
|
-
return handler.apply(instance, args);
|
|
6957
|
+
return handler.apply(instance, [draft, ...args]);
|
|
6597
6958
|
}
|
|
6598
6959
|
getHandlerAndArgs(_root, _instance, _comps) {
|
|
6599
6960
|
return null;
|
|
@@ -6602,12 +6963,16 @@ var Transaction = class {
|
|
|
6602
6963
|
// the data's real location (the dispatch `this.path` keeps intermediates). A subclass
|
|
6603
6964
|
// may override to supply a pre-resolved path (see ResponseEvent's pinned keys).
|
|
6604
6965
|
getTransactionPath() {
|
|
6605
|
-
return this.path.toTransactionPath();
|
|
6966
|
+
return this.path.toTransactionPath().compact();
|
|
6606
6967
|
}
|
|
6607
6968
|
updateRootValue(curRoot, comps) {
|
|
6608
6969
|
const txnPath = this.getTransactionPath();
|
|
6609
6970
|
const curLeaf = txnPath.lookup(curRoot);
|
|
6610
|
-
const newLeaf =
|
|
6971
|
+
const newLeaf = (0, immer_exports.produce)(curLeaf, (draft) => {
|
|
6972
|
+
const result = this.callHandler(curRoot, curLeaf, draft, comps);
|
|
6973
|
+
if (result === void 0 || result === draft) validateDraftFields(curLeaf, draft);
|
|
6974
|
+
return result;
|
|
6975
|
+
});
|
|
6611
6976
|
this._before = curLeaf;
|
|
6612
6977
|
this._after = newLeaf;
|
|
6613
6978
|
this._completion?.markSelfSettled({ value: newLeaf, old: curLeaf });
|
|
@@ -7604,14 +7969,10 @@ function lintIdToMessage(id, info) {
|
|
|
7604
7969
|
return `${info.problem} — ${info.fix}`;
|
|
7605
7970
|
case "RECEIVE_HANDLER_NOT_IMPLEMENTED":
|
|
7606
7971
|
return `Receive handler '${info.name}' is not implemented${fmtEventSuffix(info)}`;
|
|
7607
|
-
case "
|
|
7608
|
-
return `
|
|
7609
|
-
case "
|
|
7610
|
-
return `'
|
|
7611
|
-
case "METHOD_FOR_RECEIVE_HANDLER":
|
|
7612
|
-
return `'${info.name}' is a receive handler reference, but '${info.name}' is defined as a method${fmtEventSuffix(info)}`;
|
|
7613
|
-
case "FIELD_NAME_RESERVED_BY_RECORD":
|
|
7614
|
-
return `Field '${info.name}' collides with the Immutable Record API: '.${info.name}' reads the Record member, not your value — rename the field (its value is only reachable via .get('${info.name}'))`;
|
|
7972
|
+
case "EVENT_HANDLER_METHOD_NOT_ALLOWED":
|
|
7973
|
+
return `Event handler '$${info.name}' is a method reference — move it to receive and use '${info.name}'`;
|
|
7974
|
+
case "FIELD_METHOD_NAME_COLLISION":
|
|
7975
|
+
return `Field '${info.name}' shadows a method with the same name — rename either the field or method`;
|
|
7615
7976
|
case "FIELD_VAL_NOT_DEFINED":
|
|
7616
7977
|
return `Field '.${info.name}' is not defined${fmtOriginSuffix(info)}`;
|
|
7617
7978
|
case "FIELD_VAL_IS_METHOD":
|
|
@@ -8022,440 +8383,6 @@ var DragInfo = class {
|
|
|
8022
8383
|
}
|
|
8023
8384
|
};
|
|
8024
8385
|
|
|
8025
|
-
// index.js
|
|
8026
|
-
import {
|
|
8027
|
-
Collection,
|
|
8028
|
-
fromJS,
|
|
8029
|
-
get,
|
|
8030
|
-
getIn,
|
|
8031
|
-
has,
|
|
8032
|
-
hash,
|
|
8033
|
-
hasIn,
|
|
8034
|
-
is as is2,
|
|
8035
|
-
isAssociative,
|
|
8036
|
-
isCollection,
|
|
8037
|
-
isImmutable,
|
|
8038
|
-
isIndexed as isIndexed2,
|
|
8039
|
-
isKeyed as isKeyed2,
|
|
8040
|
-
isList,
|
|
8041
|
-
isMap,
|
|
8042
|
-
isMap as isMap2,
|
|
8043
|
-
isOrdered,
|
|
8044
|
-
isOrderedMap,
|
|
8045
|
-
isOrderedMap as isOrderedMap2,
|
|
8046
|
-
isOrderedSet,
|
|
8047
|
-
isPlainObject,
|
|
8048
|
-
isRecord,
|
|
8049
|
-
isSeq,
|
|
8050
|
-
isSet,
|
|
8051
|
-
isStack,
|
|
8052
|
-
isValueObject,
|
|
8053
|
-
List as List2,
|
|
8054
|
-
Map as Map2,
|
|
8055
|
-
Map as Map3,
|
|
8056
|
-
merge,
|
|
8057
|
-
mergeDeep,
|
|
8058
|
-
mergeDeepWith,
|
|
8059
|
-
mergeWith,
|
|
8060
|
-
OrderedMap as OrderedMap2,
|
|
8061
|
-
OrderedMap as OrderedMap3,
|
|
8062
|
-
OrderedSet,
|
|
8063
|
-
PairSorting,
|
|
8064
|
-
Range,
|
|
8065
|
-
Record as Record2,
|
|
8066
|
-
Repeat,
|
|
8067
|
-
remove,
|
|
8068
|
-
removeIn,
|
|
8069
|
-
Seq,
|
|
8070
|
-
Set as Set2,
|
|
8071
|
-
Set as Set3,
|
|
8072
|
-
Stack as Stack2,
|
|
8073
|
-
set,
|
|
8074
|
-
setIn,
|
|
8075
|
-
update,
|
|
8076
|
-
updateIn,
|
|
8077
|
-
version
|
|
8078
|
-
} from "immutable";
|
|
8079
|
-
|
|
8080
|
-
// src/oo.js
|
|
8081
|
-
import { Map as IMap, Set as ISet, List, OrderedMap, Record } from "immutable";
|
|
8082
|
-
var BAD_VALUE2 = /* @__PURE__ */ Symbol("BadValue");
|
|
8083
|
-
var nullCoercer = (v) => v;
|
|
8084
|
-
var Field = class {
|
|
8085
|
-
constructor(type, name, typeCheck, coercer, defaultValue = null) {
|
|
8086
|
-
this.type = type;
|
|
8087
|
-
this.name = name;
|
|
8088
|
-
this.typeCheck = typeCheck;
|
|
8089
|
-
this.coercer = coercer;
|
|
8090
|
-
this.checks = [];
|
|
8091
|
-
this.defaultValue = defaultValue;
|
|
8092
|
-
}
|
|
8093
|
-
toDataDef() {
|
|
8094
|
-
const { type, defaultValue: dv } = this;
|
|
8095
|
-
return { type, defaultValue: dv?.toJS ? dv.toJS() : dv };
|
|
8096
|
-
}
|
|
8097
|
-
getFirstFailingCheck(v) {
|
|
8098
|
-
if (!this.typeCheck.isValid(v)) return this.typeCheck;
|
|
8099
|
-
for (const check2 of this.checks) if (!check2.isValid(v)) return check2;
|
|
8100
|
-
return null;
|
|
8101
|
-
}
|
|
8102
|
-
isValid(v) {
|
|
8103
|
-
return this.getFirstFailingCheck(v) === null;
|
|
8104
|
-
}
|
|
8105
|
-
addCheck(check2) {
|
|
8106
|
-
this.checks.push(check2);
|
|
8107
|
-
return this;
|
|
8108
|
-
}
|
|
8109
|
-
coerceOr(v, defaultValue = null) {
|
|
8110
|
-
if (this.isValid(v)) return v;
|
|
8111
|
-
const v1 = this.coercer(v);
|
|
8112
|
-
return this.isValid(v1) ? v1 : defaultValue;
|
|
8113
|
-
}
|
|
8114
|
-
coerceOrDefault(v) {
|
|
8115
|
-
return this.coerceOr(v, this.defaultValue);
|
|
8116
|
-
}
|
|
8117
|
-
extendProtoForType(_proto, _uname) {
|
|
8118
|
-
}
|
|
8119
|
-
extendProto(proto) {
|
|
8120
|
-
const { name } = this;
|
|
8121
|
-
const uname = name[0].toUpperCase() + name.slice(1);
|
|
8122
|
-
const setName = `set${uname}`;
|
|
8123
|
-
const that = this;
|
|
8124
|
-
proto[setName] = function(v) {
|
|
8125
|
-
const v1 = that.coerceOr(v, BAD_VALUE2);
|
|
8126
|
-
if (v1 === BAD_VALUE2) {
|
|
8127
|
-
console.warn("invalid value", v);
|
|
8128
|
-
return this;
|
|
8129
|
-
}
|
|
8130
|
-
return this.set(name, v1);
|
|
8131
|
-
};
|
|
8132
|
-
proto[`update${uname}`] = function(fn) {
|
|
8133
|
-
return this[setName](fn(this.get(name)));
|
|
8134
|
-
};
|
|
8135
|
-
proto[`reset${uname}`] = function() {
|
|
8136
|
-
return this.set(name, that.defaultValue);
|
|
8137
|
-
};
|
|
8138
|
-
this.extendProtoForType(proto, uname);
|
|
8139
|
-
}
|
|
8140
|
-
};
|
|
8141
|
-
var Check = class {
|
|
8142
|
-
isValid(_v) {
|
|
8143
|
-
return true;
|
|
8144
|
-
}
|
|
8145
|
-
getMessage(_v) {
|
|
8146
|
-
return "Invalid";
|
|
8147
|
-
}
|
|
8148
|
-
};
|
|
8149
|
-
var CheckTypeAny = class extends Check {
|
|
8150
|
-
};
|
|
8151
|
-
var CHECK_TYPE_ANY = new CheckTypeAny();
|
|
8152
|
-
var FnCheck = class extends Check {
|
|
8153
|
-
constructor(isValidFn, getMessageFn) {
|
|
8154
|
-
super();
|
|
8155
|
-
this._isValid = isValidFn;
|
|
8156
|
-
this._getMessage = getMessageFn;
|
|
8157
|
-
}
|
|
8158
|
-
isValid(v) {
|
|
8159
|
-
return this._isValid(v);
|
|
8160
|
-
}
|
|
8161
|
-
getMessage(v) {
|
|
8162
|
-
return this._getMessage(v);
|
|
8163
|
-
}
|
|
8164
|
-
};
|
|
8165
|
-
var CHECK_TYPE_INT = new FnCheck(
|
|
8166
|
-
(v) => Number.isInteger(v),
|
|
8167
|
-
() => "Integer expected"
|
|
8168
|
-
);
|
|
8169
|
-
var CHECK_TYPE_FLOAT = new FnCheck(
|
|
8170
|
-
(v) => Number.isFinite(v),
|
|
8171
|
-
() => "Float expected"
|
|
8172
|
-
);
|
|
8173
|
-
var CHECK_TYPE_BOOL = new FnCheck(
|
|
8174
|
-
(v) => typeof v === "boolean",
|
|
8175
|
-
() => "Boolean expected"
|
|
8176
|
-
);
|
|
8177
|
-
var CHECK_TYPE_STRING = new FnCheck(
|
|
8178
|
-
(v) => typeof v === "string",
|
|
8179
|
-
() => "String expected"
|
|
8180
|
-
);
|
|
8181
|
-
var CHECK_TYPE_LIST = new FnCheck(
|
|
8182
|
-
(v) => List.isList(v),
|
|
8183
|
-
() => "List expected"
|
|
8184
|
-
);
|
|
8185
|
-
var CHECK_TYPE_MAP = new FnCheck(
|
|
8186
|
-
(v) => IMap.isMap(v),
|
|
8187
|
-
() => "Map expected"
|
|
8188
|
-
);
|
|
8189
|
-
var CHECK_TYPE_OMAP = new FnCheck(
|
|
8190
|
-
(v) => OrderedMap.isOrderedMap(v),
|
|
8191
|
-
() => "OrderedMap expected"
|
|
8192
|
-
);
|
|
8193
|
-
var CHECK_TYPE_SET = new FnCheck(
|
|
8194
|
-
(v) => ISet.isSet(v),
|
|
8195
|
-
() => "Set expected"
|
|
8196
|
-
);
|
|
8197
|
-
var boolCoercer = (v) => !!v;
|
|
8198
|
-
var FieldBool = class extends Field {
|
|
8199
|
-
constructor(name, defaultValue = false) {
|
|
8200
|
-
super("bool", name, CHECK_TYPE_BOOL, boolCoercer, defaultValue);
|
|
8201
|
-
}
|
|
8202
|
-
extendProtoForType(proto, uname) {
|
|
8203
|
-
const { name } = this;
|
|
8204
|
-
proto[`toggle${uname}`] = function() {
|
|
8205
|
-
return this.set(name, !this.get(name, false));
|
|
8206
|
-
};
|
|
8207
|
-
proto[`set${uname}`] = function(v) {
|
|
8208
|
-
return this.set(name, !!v);
|
|
8209
|
-
};
|
|
8210
|
-
}
|
|
8211
|
-
};
|
|
8212
|
-
var FieldAny = class extends Field {
|
|
8213
|
-
constructor(name, defaultValue = null) {
|
|
8214
|
-
super("any", name, CHECK_TYPE_ANY, nullCoercer, defaultValue);
|
|
8215
|
-
}
|
|
8216
|
-
toDataDef() {
|
|
8217
|
-
const { defaultValue: dv } = this;
|
|
8218
|
-
const type = getTypeName(dv) ?? "any";
|
|
8219
|
-
return { type, defaultValue: dv?.toJS ? dv.toJS() : dv };
|
|
8220
|
-
}
|
|
8221
|
-
};
|
|
8222
|
-
var stringCoercer = (v) => v?.toString?.() ?? "";
|
|
8223
|
-
var FieldString = class extends Field {
|
|
8224
|
-
constructor(name, defaultValue = "") {
|
|
8225
|
-
super("text", name, CHECK_TYPE_STRING, stringCoercer, defaultValue);
|
|
8226
|
-
}
|
|
8227
|
-
extendProtoForType(proto, _uname) {
|
|
8228
|
-
extendProtoSized(proto, this.name, "", "length");
|
|
8229
|
-
}
|
|
8230
|
-
};
|
|
8231
|
-
var intCoercer = (v) => Number.isFinite(v) ? Math.trunc(v) : null;
|
|
8232
|
-
var FieldInt = class extends Field {
|
|
8233
|
-
constructor(name, defaultValue = 0) {
|
|
8234
|
-
super("int", name, CHECK_TYPE_INT, intCoercer, defaultValue);
|
|
8235
|
-
}
|
|
8236
|
-
};
|
|
8237
|
-
var floatCoercer = (_) => null;
|
|
8238
|
-
var FieldFloat = class extends Field {
|
|
8239
|
-
constructor(name, defaultValue = 0) {
|
|
8240
|
-
super("float", name, CHECK_TYPE_FLOAT, floatCoercer, defaultValue);
|
|
8241
|
-
}
|
|
8242
|
-
};
|
|
8243
|
-
var getTypeName = (v) => v?.constructor?.getMetaClass?.()?.name;
|
|
8244
|
-
var CheckTypeName = class {
|
|
8245
|
-
constructor(typeName) {
|
|
8246
|
-
this.typeName = typeName;
|
|
8247
|
-
}
|
|
8248
|
-
isValid(v) {
|
|
8249
|
-
return getTypeName(v) === this.typeName;
|
|
8250
|
-
}
|
|
8251
|
-
getMessage(v) {
|
|
8252
|
-
const got = getTypeName(v);
|
|
8253
|
-
return `Expected "${this.typeName}", got "${got}"`;
|
|
8254
|
-
}
|
|
8255
|
-
};
|
|
8256
|
-
var FieldComp = class extends Field {
|
|
8257
|
-
constructor(type, name, args) {
|
|
8258
|
-
super(type, name, new CheckTypeName(type), nullCoercer, null);
|
|
8259
|
-
this.args = args;
|
|
8260
|
-
}
|
|
8261
|
-
toDataDef() {
|
|
8262
|
-
return { component: this.typeName, args: this.args };
|
|
8263
|
-
}
|
|
8264
|
-
};
|
|
8265
|
-
var NONE2 = /* @__PURE__ */ Symbol("NONE");
|
|
8266
|
-
function extendProtoForKeyed(proto, name, uname) {
|
|
8267
|
-
extendProtoSized(proto, name, EMPTY_LIST);
|
|
8268
|
-
proto[`setIn${uname}At`] = function(i, v) {
|
|
8269
|
-
return this.set(name, this.get(name).set(i, v));
|
|
8270
|
-
};
|
|
8271
|
-
proto[`getIn${uname}At`] = function(i, dval) {
|
|
8272
|
-
return this.get(name).get(i, dval);
|
|
8273
|
-
};
|
|
8274
|
-
proto[`updateIn${uname}At`] = function(i, fn) {
|
|
8275
|
-
const col = this.get(name);
|
|
8276
|
-
const v = col.get(i, NONE2);
|
|
8277
|
-
if (v !== NONE2) return this.set(name, col.set(i, fn(v)));
|
|
8278
|
-
console.warn("key", i, "not found in", name, col);
|
|
8279
|
-
return this;
|
|
8280
|
-
};
|
|
8281
|
-
extendDeleteInAt(proto, name, `${uname}At`);
|
|
8282
|
-
}
|
|
8283
|
-
function extendDeleteInAt(proto, name, uname) {
|
|
8284
|
-
proto[`deleteIn${uname}`] = function(v) {
|
|
8285
|
-
return this.set(name, this.get(name).delete(v));
|
|
8286
|
-
};
|
|
8287
|
-
proto[`removeIn${uname}`] = proto[`deleteIn${uname}`];
|
|
8288
|
-
}
|
|
8289
|
-
var EMPTY_LIST = List();
|
|
8290
|
-
var listCoercer = (v) => Array.isArray(v) ? List(v) : null;
|
|
8291
|
-
var FieldList = class extends Field {
|
|
8292
|
-
constructor(name, defaultValue = EMPTY_LIST) {
|
|
8293
|
-
super("list", name, CHECK_TYPE_LIST, listCoercer, defaultValue);
|
|
8294
|
-
}
|
|
8295
|
-
extendProtoForType(proto, uname) {
|
|
8296
|
-
const { name } = this;
|
|
8297
|
-
extendProtoForKeyed(proto, name, uname);
|
|
8298
|
-
proto[`pushIn${uname}`] = function(v) {
|
|
8299
|
-
return this.set(name, this.get(name).push(v));
|
|
8300
|
-
};
|
|
8301
|
-
proto[`insertIn${uname}At`] = function(i, v) {
|
|
8302
|
-
return this.set(name, this.get(name).insert(i, v));
|
|
8303
|
-
};
|
|
8304
|
-
}
|
|
8305
|
-
};
|
|
8306
|
-
var imapCoercer = (v) => IMap(v);
|
|
8307
|
-
var FieldMap = class extends Field {
|
|
8308
|
-
constructor(name, defaultValue = IMap()) {
|
|
8309
|
-
super("map", name, CHECK_TYPE_MAP, imapCoercer, defaultValue);
|
|
8310
|
-
}
|
|
8311
|
-
extendProtoForType(proto, uname) {
|
|
8312
|
-
extendProtoForKeyed(proto, this.name, uname);
|
|
8313
|
-
}
|
|
8314
|
-
};
|
|
8315
|
-
var omapCoercer = (v) => OrderedMap(v);
|
|
8316
|
-
var FieldOMap = class extends Field {
|
|
8317
|
-
constructor(name, defaultValue = OrderedMap()) {
|
|
8318
|
-
super("omap", name, CHECK_TYPE_OMAP, omapCoercer, defaultValue);
|
|
8319
|
-
}
|
|
8320
|
-
extendProtoForType(proto, uname) {
|
|
8321
|
-
extendProtoForKeyed(proto, this.name, uname);
|
|
8322
|
-
}
|
|
8323
|
-
};
|
|
8324
|
-
function extendProtoSized(proto, name, defaultEmpty, propName = "size") {
|
|
8325
|
-
proto[`${name}Len`] = function() {
|
|
8326
|
-
return this.get(name, defaultEmpty)[propName];
|
|
8327
|
-
};
|
|
8328
|
-
}
|
|
8329
|
-
var EMPTY_SET2 = ISet();
|
|
8330
|
-
var isetCoercer = (v) => Array.isArray(v) ? ISet(v) : v instanceof Set ? ISet(v) : null;
|
|
8331
|
-
var FieldSet = class extends Field {
|
|
8332
|
-
constructor(name, defaultValue = EMPTY_SET2) {
|
|
8333
|
-
super("set", name, CHECK_TYPE_SET, isetCoercer, defaultValue);
|
|
8334
|
-
}
|
|
8335
|
-
extendProtoForType(proto, uname) {
|
|
8336
|
-
const { name } = this;
|
|
8337
|
-
extendProtoSized(proto, name, EMPTY_SET2);
|
|
8338
|
-
proto[`addIn${uname}`] = function(v) {
|
|
8339
|
-
return this.set(name, this.get(name).add(v));
|
|
8340
|
-
};
|
|
8341
|
-
extendDeleteInAt(proto, name, uname);
|
|
8342
|
-
proto[`hasIn${uname}`] = function(v) {
|
|
8343
|
-
return this.get(name).has(v);
|
|
8344
|
-
};
|
|
8345
|
-
proto[`toggleIn${uname}`] = function(v) {
|
|
8346
|
-
const current = this.get(name);
|
|
8347
|
-
return this.set(name, current.has(v) ? current.delete(v) : current.add(v));
|
|
8348
|
-
};
|
|
8349
|
-
}
|
|
8350
|
-
};
|
|
8351
|
-
function mkCompField(field, scope, args) {
|
|
8352
|
-
const Comp = scope?.lookupComponent(field.type) ?? null;
|
|
8353
|
-
if (Comp === null)
|
|
8354
|
-
console.warn(
|
|
8355
|
-
scope ? `component field "${field.name}": component "${field.type}" not found in scope` : `component field "${field.name}": cannot resolve component "${field.type}" — built without a registered scope (use ${field.type}.make({}) as the default, or build via a registered component)`
|
|
8356
|
-
);
|
|
8357
|
-
return Comp?.make({ ...field.args, ...args }, { scope }) ?? null;
|
|
8358
|
-
}
|
|
8359
|
-
var ClassBuilder = class {
|
|
8360
|
-
constructor(name) {
|
|
8361
|
-
const fields = {};
|
|
8362
|
-
const compFields = /* @__PURE__ */ new Set();
|
|
8363
|
-
this.name = name;
|
|
8364
|
-
this.fields = fields;
|
|
8365
|
-
this.compFields = compFields;
|
|
8366
|
-
this._methods = {};
|
|
8367
|
-
this._statics = {
|
|
8368
|
-
make: function(inArgs = {}, opts = {}) {
|
|
8369
|
-
const args = {};
|
|
8370
|
-
const scope = opts.scope ?? this.scope;
|
|
8371
|
-
for (const key in inArgs) {
|
|
8372
|
-
const field = fields[key];
|
|
8373
|
-
if (compFields.has(key)) args[key] = mkCompField(field, scope, inArgs[key]);
|
|
8374
|
-
else if (field === void 0)
|
|
8375
|
-
console.warn("extra argument to constructor:", name, key, inArgs);
|
|
8376
|
-
else args[key] = field.coerceOrDefault(inArgs[key]);
|
|
8377
|
-
}
|
|
8378
|
-
for (const key of compFields)
|
|
8379
|
-
if (args[key] === void 0) args[key] = mkCompField(fields[key], scope, inArgs[key]);
|
|
8380
|
-
return this(args);
|
|
8381
|
-
}
|
|
8382
|
-
};
|
|
8383
|
-
}
|
|
8384
|
-
build() {
|
|
8385
|
-
const fieldVals = {};
|
|
8386
|
-
const proto = {};
|
|
8387
|
-
const { name, _methods, fields } = this;
|
|
8388
|
-
for (const fieldName in fields) {
|
|
8389
|
-
const field = fields[fieldName];
|
|
8390
|
-
fieldVals[fieldName] = field.defaultValue;
|
|
8391
|
-
field.extendProto(proto);
|
|
8392
|
-
}
|
|
8393
|
-
const Class = { [name]: Record(fieldVals, name) }[name];
|
|
8394
|
-
Object.assign(Class.prototype, proto, _methods);
|
|
8395
|
-
const metaClass = { fields, name, methods: _methods };
|
|
8396
|
-
Object.assign(Class, this._statics, { getMetaClass: () => metaClass });
|
|
8397
|
-
return Class;
|
|
8398
|
-
}
|
|
8399
|
-
methods(proto) {
|
|
8400
|
-
for (const k in proto) this._methods[k] = proto[k];
|
|
8401
|
-
}
|
|
8402
|
-
statics(proto) {
|
|
8403
|
-
for (const k in proto) this._statics[k] = proto[k];
|
|
8404
|
-
}
|
|
8405
|
-
addField(name, dval, FieldCls) {
|
|
8406
|
-
const field = new FieldCls(name, dval);
|
|
8407
|
-
this.fields[name] = field;
|
|
8408
|
-
return field;
|
|
8409
|
-
}
|
|
8410
|
-
addCompField(name, type, args) {
|
|
8411
|
-
const field = new FieldComp(type, name, args);
|
|
8412
|
-
this.compFields.add(name);
|
|
8413
|
-
this.fields[name] = field;
|
|
8414
|
-
return field;
|
|
8415
|
-
}
|
|
8416
|
-
};
|
|
8417
|
-
var FIELD_CLASS = /* @__PURE__ */ Symbol.for("tutuca.fieldClass");
|
|
8418
|
-
var fieldsByTypeName = {
|
|
8419
|
-
text: FieldString,
|
|
8420
|
-
int: FieldInt,
|
|
8421
|
-
float: FieldFloat,
|
|
8422
|
-
bool: FieldBool,
|
|
8423
|
-
list: FieldList,
|
|
8424
|
-
map: FieldMap,
|
|
8425
|
-
omap: FieldOMap,
|
|
8426
|
-
set: FieldSet,
|
|
8427
|
-
any: FieldAny
|
|
8428
|
-
};
|
|
8429
|
-
function classFromData(name, { fields = {}, methods, statics }) {
|
|
8430
|
-
const b = new ClassBuilder(name);
|
|
8431
|
-
for (const field in fields) {
|
|
8432
|
-
const value = fields[field];
|
|
8433
|
-
const type = typeof value;
|
|
8434
|
-
if (type === "string") b.addField(field, value, FieldString);
|
|
8435
|
-
else if (type === "number") b.addField(field, value, FieldFloat);
|
|
8436
|
-
else if (type === "boolean") b.addField(field, value, FieldBool);
|
|
8437
|
-
else if (List.isList(value) || Array.isArray(value)) b.addField(field, List(value), FieldList);
|
|
8438
|
-
else if (ISet.isSet(value) || value instanceof Set) b.addField(field, ISet(value), FieldSet);
|
|
8439
|
-
else if (OrderedMap.isOrderedMap(value)) b.addField(field, value, FieldOMap);
|
|
8440
|
-
else if (value?.type && value?.defaultValue !== void 0) {
|
|
8441
|
-
const Field2 = fieldsByTypeName[value.type] ?? FieldAny;
|
|
8442
|
-
b.addField(field, new Field2().coerceOr(value.defaultValue), Field2);
|
|
8443
|
-
} else if (value?.component && value?.args !== void 0)
|
|
8444
|
-
b.addCompField(field, value.component, value.args);
|
|
8445
|
-
else if (IMap.isMap(value) || value?.constructor === Object)
|
|
8446
|
-
b.addField(field, IMap(value), FieldMap);
|
|
8447
|
-
else {
|
|
8448
|
-
const Field2 = value?.[FIELD_CLASS] ?? FieldAny;
|
|
8449
|
-
b.addField(field, value, Field2);
|
|
8450
|
-
}
|
|
8451
|
-
}
|
|
8452
|
-
if (methods) b.methods(methods);
|
|
8453
|
-
if (statics) b.statics(statics);
|
|
8454
|
-
return b.build();
|
|
8455
|
-
}
|
|
8456
|
-
Component.fromSpec = (opts) => new Component(classFromData(opts.name, opts), opts);
|
|
8457
|
-
var component = (opts) => Component.fromSpec(opts);
|
|
8458
|
-
|
|
8459
8386
|
// index.js
|
|
8460
8387
|
var css = String.raw;
|
|
8461
8388
|
var html = String.raw;
|
|
@@ -8508,7 +8435,6 @@ function resolveAlter(Comp, name) {
|
|
|
8508
8435
|
}
|
|
8509
8436
|
return fn;
|
|
8510
8437
|
}
|
|
8511
|
-
var seqGet = (seq, key) => Array.isArray(seq) ? seq[key] : seq.get ? seq.get(key) : seq[key];
|
|
8512
8438
|
function collectIterBindings(Comp, compInstance, seq, opts = {}) {
|
|
8513
8439
|
const whenFn = resolveAlter(Comp, opts.when) ?? filterAlwaysTrue;
|
|
8514
8440
|
const loopWithFn = resolveAlter(Comp, opts.loopWith) ?? nullLoopWith;
|
|
@@ -8553,157 +8479,10 @@ function getSignature(name, fn) {
|
|
|
8553
8479
|
const params = m ? m[1].trim() : "";
|
|
8554
8480
|
return `${name}(${params})`;
|
|
8555
8481
|
}
|
|
8556
|
-
function getFieldMethods(field) {
|
|
8557
|
-
const { name, type } = field;
|
|
8558
|
-
const uname = name[0].toUpperCase() + name.slice(1);
|
|
8559
|
-
const methods = [
|
|
8560
|
-
{ name: `set${uname}`, sig: `set${uname}(v)`, desc: "Set value" },
|
|
8561
|
-
{
|
|
8562
|
-
name: `update${uname}`,
|
|
8563
|
-
sig: `update${uname}(fn)`,
|
|
8564
|
-
desc: "Update value with function"
|
|
8565
|
-
},
|
|
8566
|
-
{
|
|
8567
|
-
name: `reset${uname}`,
|
|
8568
|
-
sig: `reset${uname}()`,
|
|
8569
|
-
desc: "Reset to default value"
|
|
8570
|
-
}
|
|
8571
|
-
];
|
|
8572
|
-
switch (type) {
|
|
8573
|
-
case "bool":
|
|
8574
|
-
methods[0].desc = "Set value (coerces to boolean)";
|
|
8575
|
-
methods.push({
|
|
8576
|
-
name: `toggle${uname}`,
|
|
8577
|
-
sig: `toggle${uname}()`,
|
|
8578
|
-
desc: "Toggle boolean value"
|
|
8579
|
-
});
|
|
8580
|
-
break;
|
|
8581
|
-
case "int":
|
|
8582
|
-
case "float":
|
|
8583
|
-
case "any":
|
|
8584
|
-
break;
|
|
8585
|
-
case "text":
|
|
8586
|
-
methods.push({
|
|
8587
|
-
name: `${name}Len`,
|
|
8588
|
-
sig: `${name}Len()`,
|
|
8589
|
-
desc: "Get string length"
|
|
8590
|
-
});
|
|
8591
|
-
break;
|
|
8592
|
-
case "list":
|
|
8593
|
-
methods.push(
|
|
8594
|
-
{ name: `${name}Len`, sig: `${name}Len()`, desc: "Get list size" },
|
|
8595
|
-
{
|
|
8596
|
-
name: `setIn${uname}At`,
|
|
8597
|
-
sig: `setIn${uname}At(i, v)`,
|
|
8598
|
-
desc: "Set item at index"
|
|
8599
|
-
},
|
|
8600
|
-
{
|
|
8601
|
-
name: `getIn${uname}At`,
|
|
8602
|
-
sig: `getIn${uname}At(i, defaultValue)`,
|
|
8603
|
-
desc: "Get item at index"
|
|
8604
|
-
},
|
|
8605
|
-
{
|
|
8606
|
-
name: `updateIn${uname}At`,
|
|
8607
|
-
sig: `updateIn${uname}At(i, fn)`,
|
|
8608
|
-
desc: "Update item at index with function"
|
|
8609
|
-
},
|
|
8610
|
-
{
|
|
8611
|
-
name: `deleteIn${uname}At`,
|
|
8612
|
-
sig: `deleteIn${uname}At(i)`,
|
|
8613
|
-
desc: "Delete item at index"
|
|
8614
|
-
},
|
|
8615
|
-
{
|
|
8616
|
-
name: `removeIn${uname}At`,
|
|
8617
|
-
sig: `removeIn${uname}At(i)`,
|
|
8618
|
-
desc: "Delete item at index (alias)"
|
|
8619
|
-
},
|
|
8620
|
-
{
|
|
8621
|
-
name: `pushIn${uname}`,
|
|
8622
|
-
sig: `pushIn${uname}(v)`,
|
|
8623
|
-
desc: "Push item to end"
|
|
8624
|
-
},
|
|
8625
|
-
{
|
|
8626
|
-
name: `insertIn${uname}At`,
|
|
8627
|
-
sig: `insertIn${uname}At(i, v)`,
|
|
8628
|
-
desc: "Insert item at index"
|
|
8629
|
-
}
|
|
8630
|
-
);
|
|
8631
|
-
break;
|
|
8632
|
-
case "map":
|
|
8633
|
-
case "omap": {
|
|
8634
|
-
const label = type === "omap" ? "ordered map" : "map";
|
|
8635
|
-
methods.push(
|
|
8636
|
-
{
|
|
8637
|
-
name: `${name}Len`,
|
|
8638
|
-
sig: `${name}Len()`,
|
|
8639
|
-
desc: `Get ${label} size`
|
|
8640
|
-
},
|
|
8641
|
-
{
|
|
8642
|
-
name: `setIn${uname}At`,
|
|
8643
|
-
sig: `setIn${uname}At(key, v)`,
|
|
8644
|
-
desc: "Set value at key"
|
|
8645
|
-
},
|
|
8646
|
-
{
|
|
8647
|
-
name: `getIn${uname}At`,
|
|
8648
|
-
sig: `getIn${uname}At(key, defaultValue)`,
|
|
8649
|
-
desc: "Get value at key"
|
|
8650
|
-
},
|
|
8651
|
-
{
|
|
8652
|
-
name: `updateIn${uname}At`,
|
|
8653
|
-
sig: `updateIn${uname}At(key, fn)`,
|
|
8654
|
-
desc: "Update value at key with function"
|
|
8655
|
-
},
|
|
8656
|
-
{
|
|
8657
|
-
name: `deleteIn${uname}At`,
|
|
8658
|
-
sig: `deleteIn${uname}At(key)`,
|
|
8659
|
-
desc: "Delete entry at key"
|
|
8660
|
-
},
|
|
8661
|
-
{
|
|
8662
|
-
name: `removeIn${uname}At`,
|
|
8663
|
-
sig: `removeIn${uname}At(key)`,
|
|
8664
|
-
desc: "Delete entry at key (alias)"
|
|
8665
|
-
}
|
|
8666
|
-
);
|
|
8667
|
-
break;
|
|
8668
|
-
}
|
|
8669
|
-
case "set":
|
|
8670
|
-
methods.push(
|
|
8671
|
-
{ name: `${name}Len`, sig: `${name}Len()`, desc: "Get set size" },
|
|
8672
|
-
{
|
|
8673
|
-
name: `addIn${uname}`,
|
|
8674
|
-
sig: `addIn${uname}(v)`,
|
|
8675
|
-
desc: "Add value to set"
|
|
8676
|
-
},
|
|
8677
|
-
{
|
|
8678
|
-
name: `deleteIn${uname}`,
|
|
8679
|
-
sig: `deleteIn${uname}(v)`,
|
|
8680
|
-
desc: "Remove value from set"
|
|
8681
|
-
},
|
|
8682
|
-
{
|
|
8683
|
-
name: `removeIn${uname}`,
|
|
8684
|
-
sig: `removeIn${uname}(v)`,
|
|
8685
|
-
desc: "Remove value from set (alias)"
|
|
8686
|
-
},
|
|
8687
|
-
{
|
|
8688
|
-
name: `hasIn${uname}`,
|
|
8689
|
-
sig: `hasIn${uname}(v)`,
|
|
8690
|
-
desc: "Check if value is in set"
|
|
8691
|
-
},
|
|
8692
|
-
{
|
|
8693
|
-
name: `toggleIn${uname}`,
|
|
8694
|
-
sig: `toggleIn${uname}(v)`,
|
|
8695
|
-
desc: "Toggle value in set"
|
|
8696
|
-
}
|
|
8697
|
-
);
|
|
8698
|
-
break;
|
|
8699
|
-
default:
|
|
8700
|
-
break;
|
|
8701
|
-
}
|
|
8702
|
-
return methods;
|
|
8703
|
-
}
|
|
8704
8482
|
function serializeDefault(v) {
|
|
8705
8483
|
if (v === null || v === void 0) return v;
|
|
8706
|
-
if (v
|
|
8484
|
+
if (v instanceof Map) return Object.fromEntries(v);
|
|
8485
|
+
if (v instanceof Set) return [...v];
|
|
8707
8486
|
return v;
|
|
8708
8487
|
}
|
|
8709
8488
|
function getComponentDoc(comp) {
|
|
@@ -8723,7 +8502,7 @@ function getComponentDoc(comp) {
|
|
|
8723
8502
|
name: fieldName,
|
|
8724
8503
|
type: field.type,
|
|
8725
8504
|
default: serializeDefault(field.defaultValue),
|
|
8726
|
-
methods:
|
|
8505
|
+
methods: []
|
|
8727
8506
|
});
|
|
8728
8507
|
}
|
|
8729
8508
|
return {
|
|
@@ -8759,7 +8538,7 @@ function shadowCheckComponent(Comp) {
|
|
|
8759
8538
|
shadowComp.views = shadowViews;
|
|
8760
8539
|
return checkComponent(shadowComp).reports;
|
|
8761
8540
|
}
|
|
8762
|
-
function
|
|
8541
|
+
function check2(app) {
|
|
8763
8542
|
const counts = { error: 0, warn: 0, hint: 0 };
|
|
8764
8543
|
for (const Comp of app.comps.byId.values()) {
|
|
8765
8544
|
const reports = shadowCheckComponent(Comp);
|
|
@@ -8824,7 +8603,6 @@ export {
|
|
|
8824
8603
|
BINDING_MEMBER_TOO_DEEP,
|
|
8825
8604
|
COMP_FIELD_BAD_SHAPE,
|
|
8826
8605
|
CONSTANT_CONDITION,
|
|
8827
|
-
Collection,
|
|
8828
8606
|
ComponentDocs,
|
|
8829
8607
|
ComponentList,
|
|
8830
8608
|
ComponentSummary,
|
|
@@ -8834,16 +8612,15 @@ export {
|
|
|
8834
8612
|
DYN_VAL_NOT_DEFINED,
|
|
8835
8613
|
Describe,
|
|
8836
8614
|
DescribeResult,
|
|
8615
|
+
EVENT_HANDLER_METHOD_NOT_ALLOWED,
|
|
8837
8616
|
ExampleIndex,
|
|
8838
8617
|
FIELD_CLASS,
|
|
8839
|
-
|
|
8618
|
+
FIELD_METHOD_NAME_COLLISION,
|
|
8840
8619
|
FIELD_VAL_IS_METHOD,
|
|
8841
8620
|
FIELD_VAL_NOT_DEFINED,
|
|
8842
8621
|
GLOBAL_SELECTOR_IN_SCOPED_STYLE,
|
|
8843
8622
|
HANDLER_NAME_COLLISION,
|
|
8844
8623
|
IF_NO_BRANCH_SET,
|
|
8845
|
-
Map3 as IMap,
|
|
8846
|
-
Set3 as ISet,
|
|
8847
8624
|
LOOKUP_BAD_SHAPE,
|
|
8848
8625
|
LOOKUP_TARGET_MALFORMED,
|
|
8849
8626
|
LintClassCollectorCtx,
|
|
@@ -8852,42 +8629,27 @@ export {
|
|
|
8852
8629
|
LintFinding,
|
|
8853
8630
|
LintParseContext,
|
|
8854
8631
|
LintReport,
|
|
8855
|
-
List2 as List,
|
|
8856
8632
|
MAYBE_ADD_AT_PREFIX,
|
|
8857
8633
|
MAYBE_DROP_AT_PREFIX,
|
|
8858
|
-
METHOD_FOR_RECEIVE_HANDLER,
|
|
8859
8634
|
METHOD_VAL_IS_FIELD,
|
|
8860
8635
|
METHOD_VAL_NOT_DEFINED,
|
|
8861
|
-
Map2 as Map,
|
|
8862
8636
|
ModuleInfo,
|
|
8863
8637
|
ModuleTestReport,
|
|
8864
8638
|
ModuleTests,
|
|
8865
|
-
OrderedMap3 as OMap,
|
|
8866
|
-
OrderedMap2 as OrderedMap,
|
|
8867
|
-
OrderedSet,
|
|
8868
8639
|
PASS,
|
|
8869
8640
|
PLACEHOLDERLESS_TEMPLATE_STRING,
|
|
8870
8641
|
PROVIDE_NOT_ADDRESSABLE,
|
|
8871
|
-
PairSorting,
|
|
8872
8642
|
ParseContext,
|
|
8873
|
-
RECEIVE_HANDLER_FOR_METHOD,
|
|
8874
|
-
RECEIVE_HANDLER_METHOD_NOT_IMPLEMENTED,
|
|
8875
8643
|
RECEIVE_HANDLER_NOT_IMPLEMENTED,
|
|
8876
8644
|
REDUNDANT_TEMPLATE_STRING,
|
|
8877
8645
|
RENDER_IT_OUTSIDE_OF_LOOP,
|
|
8878
8646
|
RETIRED_CTX_VERB,
|
|
8879
8647
|
RETIRED_HANDLER_BUCKET,
|
|
8880
|
-
Range,
|
|
8881
|
-
Record2 as Record,
|
|
8882
8648
|
RenderBatch,
|
|
8883
8649
|
RenderedExample,
|
|
8884
8650
|
RenderedSection,
|
|
8885
|
-
Repeat,
|
|
8886
8651
|
SEQ_INFO,
|
|
8887
8652
|
SUGGEST_BINDING_MEMBER,
|
|
8888
|
-
Seq,
|
|
8889
|
-
Set2 as Set,
|
|
8890
|
-
Stack2 as Stack,
|
|
8891
8653
|
TOP_LEVEL_AT_RULE_IN_SCOPED_STYLE,
|
|
8892
8654
|
Test,
|
|
8893
8655
|
TestReport,
|
|
@@ -8902,7 +8664,7 @@ export {
|
|
|
8902
8664
|
UNKNOWN_X_OP,
|
|
8903
8665
|
UNSUPPORTED_EXPR_SYNTAX,
|
|
8904
8666
|
X_OP_IGNORES_CHILDREN,
|
|
8905
|
-
check,
|
|
8667
|
+
check2 as check,
|
|
8906
8668
|
checkComponent,
|
|
8907
8669
|
collectIterBindings,
|
|
8908
8670
|
compileClassesToStyle,
|
|
@@ -8913,54 +8675,18 @@ export {
|
|
|
8913
8675
|
docComponents,
|
|
8914
8676
|
drive,
|
|
8915
8677
|
export_expect as expect,
|
|
8916
|
-
fromJS,
|
|
8917
|
-
get,
|
|
8918
|
-
getIn,
|
|
8919
|
-
has,
|
|
8920
|
-
hasIn,
|
|
8921
|
-
hash,
|
|
8922
8678
|
html,
|
|
8923
8679
|
injectCss,
|
|
8924
|
-
is2 as is,
|
|
8925
|
-
isAssociative,
|
|
8926
|
-
isCollection,
|
|
8927
|
-
isMap2 as isIMap,
|
|
8928
|
-
isImmutable,
|
|
8929
|
-
isIndexed2 as isIndexed,
|
|
8930
|
-
isKeyed2 as isKeyed,
|
|
8931
|
-
isList,
|
|
8932
|
-
isMap,
|
|
8933
|
-
isOrderedMap2 as isOMap,
|
|
8934
|
-
isOrdered,
|
|
8935
|
-
isOrderedMap,
|
|
8936
|
-
isOrderedSet,
|
|
8937
|
-
isPlainObject,
|
|
8938
|
-
isRecord,
|
|
8939
|
-
isSeq,
|
|
8940
|
-
isSet,
|
|
8941
|
-
isStack,
|
|
8942
|
-
isValueObject,
|
|
8943
8680
|
lintIdToMessage,
|
|
8944
8681
|
macro,
|
|
8945
8682
|
makeCollector,
|
|
8946
|
-
merge,
|
|
8947
|
-
mergeDeep,
|
|
8948
|
-
mergeDeepWith,
|
|
8949
|
-
mergeWith,
|
|
8950
8683
|
phaseOps,
|
|
8951
|
-
remove,
|
|
8952
|
-
removeIn,
|
|
8953
8684
|
reportTestReportToConsole,
|
|
8954
8685
|
resolveArgs,
|
|
8955
8686
|
rootDispatcher,
|
|
8956
8687
|
runTests,
|
|
8957
|
-
set,
|
|
8958
|
-
setIn,
|
|
8959
8688
|
shadowCheckComponent,
|
|
8960
8689
|
suggestionToMessage,
|
|
8961
8690
|
test,
|
|
8962
|
-
tutuca
|
|
8963
|
-
update,
|
|
8964
|
-
updateIn,
|
|
8965
|
-
version
|
|
8691
|
+
tutuca
|
|
8966
8692
|
};
|