attaform 0.28.0 → 0.29.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.
Files changed (64) hide show
  1. package/dist/abstract.d.mts +5 -5
  2. package/dist/abstract.mjs +4 -4
  3. package/dist/chunks/fingerprint.mjs +1 -1
  4. package/dist/chunks/fingerprint2.mjs +2 -2
  5. package/dist/dev/abstract.mjs +4 -4
  6. package/dist/dev/chunks/devtools.mjs +1 -1
  7. package/dist/dev/chunks/fingerprint.mjs +1 -1
  8. package/dist/dev/chunks/fingerprint2.mjs +2 -2
  9. package/dist/dev/directive.mjs +1 -1
  10. package/dist/dev/history.mjs +1 -1
  11. package/dist/dev/index.mjs +5 -5
  12. package/dist/dev/runtime/plugins/attaform.mjs +1 -1
  13. package/dist/dev/shared/{attaform-dev.Dr2YzS5B.mjs → attaform-dev.A-TpJW0B.mjs} +11 -1
  14. package/dist/dev/shared/{attaform-dev.oYrkP9dj.mjs → attaform-dev.BO-71R54.mjs} +51 -158
  15. package/dist/dev/shared/{attaform-dev.6qxD-Yqo.mjs → attaform-dev.BgM6FdtA.mjs} +143 -36
  16. package/dist/{shared/attaform.h0i6LijT.mjs → dev/shared/attaform-dev.ButTkwHd.mjs} +149 -16
  17. package/dist/{shared/attaform.BJGA_UOS.mjs → dev/shared/attaform-dev.BxfsuwBR.mjs} +8 -0
  18. package/dist/dev/shared/{attaform-dev.P7cseiEG.mjs → attaform-dev.D8aoKb89.mjs} +13 -4
  19. package/dist/dev/shared/{attaform-dev.BXE2cr0L.mjs → attaform-dev.DD5m2W51.mjs} +1 -1
  20. package/dist/dev/shared/{attaform-dev.WmuhD_CZ.mjs → attaform-dev.DHuydLAC.mjs} +344 -96
  21. package/dist/dev/shared/{attaform-dev.BR8u0YOZ.mjs → attaform-dev.DrzObAZo.mjs} +4 -4
  22. package/dist/dev/shared/{attaform-dev.D2I8e_Mm.mjs → attaform-dev.q6UutkCx.mjs} +170 -132
  23. package/dist/dev/zod-v3.mjs +6 -6
  24. package/dist/dev/zod-v4.mjs +6 -6
  25. package/dist/dev/zod.mjs +5 -5
  26. package/dist/directive.d.mts +2 -2
  27. package/dist/directive.mjs +1 -1
  28. package/dist/history.d.mts +1 -1
  29. package/dist/history.mjs +1 -1
  30. package/dist/index.d.mts +9 -7
  31. package/dist/index.mjs +5 -5
  32. package/dist/nuxt.d.mts +10 -10
  33. package/dist/runtime/plugins/attaform.mjs +1 -1
  34. package/dist/shared/{attaform.C09fpdLS.mjs → attaform.B0dKL8ST.mjs} +143 -36
  35. package/dist/shared/{attaform.Cs2Rbdlo.mjs → attaform.BK0cgu2K.mjs} +123 -139
  36. package/dist/shared/{attaform.D6DCnnQu.mjs → attaform.BndjUUYX.mjs} +4 -4
  37. package/dist/{dev/shared/attaform-dev.BJGA_UOS.mjs → shared/attaform.BxfsuwBR.mjs} +8 -0
  38. package/dist/shared/{attaform.NLmerepI.mjs → attaform.C2MVyuxC.mjs} +42 -151
  39. package/dist/shared/{attaform.B4VkS43-.d.mts → attaform.CIWLMY-R.d.mts} +1 -1
  40. package/dist/shared/{attaform.B8k8JrmK.mjs → attaform.CZMAYwSK.mjs} +338 -95
  41. package/dist/shared/{attaform.wfY8XFvm.mjs → attaform.CZYt_5N_.mjs} +11 -1
  42. package/dist/shared/{attaform.Cgu-hdSb.d.mts → attaform.CsoeRi3P.d.mts} +224 -32
  43. package/dist/{dev/shared/attaform-dev.By4PRjt0.mjs → shared/attaform.Cvao8bW5.mjs} +132 -22
  44. package/dist/shared/{attaform.Dq4vWxuG.mjs → attaform.D0x-qSXm.mjs} +1 -1
  45. package/dist/shared/{attaform.CJP3RkGa.mjs → attaform.D1fnTifF.mjs} +168 -132
  46. package/dist/shared/{attaform.D5V4tZWq.d.mts → attaform.DDtqHYv1.d.mts} +88 -7
  47. package/dist/shared/{attaform.uLbun31C.mjs → attaform.DffRL5pP.mjs} +12 -4
  48. package/dist/shared/{attaform.JfSWdEcb.d.mts → attaform.axHXVQO7.d.mts} +1 -1
  49. package/dist/transforms.d.mts +0 -22
  50. package/dist/transforms.mjs +1 -1
  51. package/dist/vite.d.mts +13 -4
  52. package/dist/vite.mjs +3 -2
  53. package/dist/zod-v3.d.mts +6 -4
  54. package/dist/zod-v3.mjs +6 -6
  55. package/dist/zod-v4.d.mts +14 -27
  56. package/dist/zod-v4.mjs +6 -6
  57. package/dist/zod.d.mts +4 -4
  58. package/dist/zod.mjs +5 -5
  59. package/package.json +17 -14
  60. package/skills/attaform/SKILL.md +5 -2
  61. package/skills/attaform/references/custom-components.md +7 -2
  62. package/skills/attaform/references/errors.md +8 -3
  63. package/skills/attaform/references/saving.md +77 -0
  64. package/skills/attaform/references/wizards.md +10 -8
@@ -1,16 +1,30 @@
1
- import { A as AttaformErrorCode, n as isPlainRecord, s as slimKindOf } from './attaform-dev.WmuhD_CZ.mjs';
2
- import { e as canonicalizePath } from './attaform-dev.Dr2YzS5B.mjs';
3
- import { a as safeOwnRead, b as safeAssign } from './attaform-dev.By4PRjt0.mjs';
1
+ import { A as AttaformErrorCode, n as isPlainRecord, s as slimKindOf, o as crossCopyState } from './attaform-dev.DHuydLAC.mjs';
2
+ import { e as canonicalizePath, h as SET_MEMBER_SEGMENT } from './attaform-dev.A-TpJW0B.mjs';
3
+ import { a as safeOwnRead, b as safeAssign } from './attaform-dev.ButTkwHd.mjs';
4
4
 
5
5
  const PATH_SEPARATOR = ".";
6
+ function isOpaqueKind(kind) {
7
+ return kind === "any" || kind === "unknown" || kind === "custom";
8
+ }
6
9
  function createAbstractSchema(rootSchema, intro, services, formKey, options) {
7
10
  const maxRecursionDepth = options.maxRecursionDepth;
8
11
  const leafCache = /* @__PURE__ */ new Map();
9
12
  const preprocessOrCoerceCache = /* @__PURE__ */ new Map();
13
+ const opaqueLeafCache = /* @__PURE__ */ new Map();
10
14
  const discriminatorCache = /* @__PURE__ */ new Map();
15
+ const entryKeyKindCache = /* @__PURE__ */ new Map();
11
16
  let asyncValidationFlag = null;
12
17
  let containerRefineFlag = null;
13
18
  let discriminatedUnionFlag = null;
19
+ function mapKeySegmentKind(schema) {
20
+ const keyType = intro.getMapKeyType(schema);
21
+ if (keyType === void 0) return void 0;
22
+ const kinds = services.slimPrimitivesOf(keyType, maxRecursionDepth);
23
+ const string = kinds.has("string");
24
+ const number = kinds.has("number");
25
+ if (string === number) return void 0;
26
+ return string ? "string" : "number";
27
+ }
14
28
  function computeDiscriminator(path) {
15
29
  const candidates = path.length === 0 ? [rootSchema] : services.getNestedSchemasAtPath(rootSchema, path, maxRecursionDepth);
16
30
  let matchedUnion;
@@ -102,6 +116,32 @@ function createAbstractSchema(rootSchema, intro, services, formKey, options) {
102
116
  if (resolved.length === 0) return false;
103
117
  return resolved.every((s) => intro.kindOf(services.peelAllWrappers(s)) === "object");
104
118
  },
119
+ entryKeyKindAtPath(path) {
120
+ const cacheKey = canonicalizePath(path).key;
121
+ if (entryKeyKindCache.has(cacheKey)) return entryKeyKindCache.get(cacheKey);
122
+ const resolved = path.length === 0 ? [rootSchema] : services.getNestedSchemasAtPath(rootSchema, path, maxRecursionDepth);
123
+ let answer;
124
+ const only = resolved.length === 1 ? resolved[0] : void 0;
125
+ if (only !== void 0) {
126
+ switch (intro.kindOf(services.peelAllWrappers(only))) {
127
+ case "array":
128
+ case "tuple":
129
+ answer = "number";
130
+ break;
131
+ case "object":
132
+ case "record":
133
+ answer = "string";
134
+ break;
135
+ case "map":
136
+ answer = mapKeySegmentKind(services.peelAllWrappers(only));
137
+ break;
138
+ default:
139
+ answer = void 0;
140
+ }
141
+ }
142
+ entryKeyKindCache.set(cacheKey, answer);
143
+ return answer;
144
+ },
105
145
  getSchemasAtPath(path) {
106
146
  const resolved = services.getNestedSchemasInSlimMode(rootSchema, path, maxRecursionDepth);
107
147
  if (resolved.length === 0) return [];
@@ -123,8 +163,9 @@ function createAbstractSchema(rootSchema, intro, services, formKey, options) {
123
163
  const cacheKey = canonicalizePath(path).key;
124
164
  const cached = leafCache.get(cacheKey);
125
165
  if (cached !== void 0) return cached;
126
- const prim = this.getSlimPrimitiveTypesAtPath(path);
127
- const isLeaf = prim.size > 0 && !prim.has("object") && !prim.has("array") && !prim.has("map") && !prim.has("set");
166
+ const opaque = path.length > 0 && this.isOpaqueLeafAtPath(path);
167
+ const prim = opaque ? void 0 : this.getSlimPrimitiveTypesAtPath(path);
168
+ const isLeaf = opaque || prim !== void 0 && prim.size > 0 && !prim.has("object") && !prim.has("array") && !prim.has("map") && !prim.has("set");
128
169
  leafCache.set(cacheKey, isLeaf);
129
170
  return isLeaf;
130
171
  },
@@ -146,6 +187,17 @@ function createAbstractSchema(rootSchema, intro, services, formKey, options) {
146
187
  preprocessOrCoerceCache.set(cacheKey, hit);
147
188
  return hit;
148
189
  },
190
+ isOpaqueLeafAtPath(path) {
191
+ const cacheKey = canonicalizePath(path).key;
192
+ const cached = opaqueLeafCache.get(cacheKey);
193
+ if (cached !== void 0) return cached;
194
+ const resolved = path.length === 0 ? [rootSchema] : services.getNestedSchemasAtPath(rootSchema, path, maxRecursionDepth);
195
+ const opaque = resolved.length > 0 && resolved.every(
196
+ (candidate) => isOpaqueKind(intro.kindOf(services.peelAllWrappers(candidate)))
197
+ );
198
+ opaqueLeafCache.set(cacheKey, opaque);
199
+ return opaque;
200
+ },
149
201
  isRequiredAtPath(path) {
150
202
  if (path.length === 0) return true;
151
203
  const resolved = services.getNestedSchemasAtPath(rootSchema, path, maxRecursionDepth);
@@ -289,6 +341,7 @@ function walkPathSegments(schema, segments, intro, maxDepth, lazyDepth) {
289
341
  return inner === void 0 ? [] : walkPathSegments(inner, rest, intro, maxDepth, lazyDepth);
290
342
  }
291
343
  case "set": {
344
+ if (head !== SET_MEMBER_SEGMENT) return [];
292
345
  const inner = intro.getSetValueType(schema);
293
346
  return inner === void 0 ? [] : walkPathSegments(inner, rest, intro, maxDepth, lazyDepth);
294
347
  }
@@ -296,6 +349,10 @@ function walkPathSegments(schema, segments, intro, maxDepth, lazyDepth) {
296
349
  const inner = intro.getRecordValueType(schema);
297
350
  return inner === void 0 ? [] : walkPathSegments(inner, rest, intro, maxDepth, lazyDepth);
298
351
  }
352
+ case "map": {
353
+ const inner = intro.getMapValueType(schema);
354
+ return inner === void 0 ? [] : walkPathSegments(inner, rest, intro, maxDepth, lazyDepth);
355
+ }
299
356
  case "tuple": {
300
357
  const index = Number(head);
301
358
  if (!Number.isInteger(index)) return [];
@@ -349,11 +406,13 @@ function walkPathSegments(schema, segments, intro, maxDepth, lazyDepth) {
349
406
  const rightResults = right === void 0 ? [] : walkPathSegments(right, segments, intro, maxDepth, lazyDepth);
350
407
  return [...leftResults, ...rightResults];
351
408
  }
352
- // Leaves — can't descend further. The unsupported kinds (`map` /
353
- // `symbol` / `function` / `promise`) are rejected at adapter
354
- // construction by `assertSupportedKinds`; falling through to `[]`
355
- // keeps the walker defensive in case construction is skipped
356
- // (e.g. a downstream test instantiates a sub-schema directly).
409
+ // Leaves — can't descend further. Opaque leaves (`any` /
410
+ // `unknown` / `custom`) land here too and `[]` is the truthful
411
+ // answer: the schema declares no sub-paths under them, so none are
412
+ // fabricated. `symbol` / `function` / `promise` hold a value
413
+ // without declaring anything inside it and land here for the same
414
+ // reason. No kind is refused at construction (#607), so this is
415
+ // the only branch they ever take.
357
416
  default:
358
417
  return [];
359
418
  }
@@ -461,6 +520,15 @@ function fixNode(schema, value, ctx, lazyDepth) {
461
520
  }
462
521
  return value;
463
522
  }
523
+ case "map": {
524
+ if (!(value instanceof Map)) return value;
525
+ const valueType = intro.getMapValueType(schema);
526
+ if (valueType === void 0) return value;
527
+ for (const [key, entry] of [...value]) {
528
+ value.set(key, fixNode(valueType, entry, ctx, lazyDepth));
529
+ }
530
+ return value;
531
+ }
464
532
  case "intersection": {
465
533
  const left = intro.getIntersectionLeft(schema);
466
534
  const right = intro.getIntersectionRight(schema);
@@ -684,58 +752,63 @@ function deriveDefaultWalk(schema, useDefault, intro, maxDepth, ctx, lazyDepth =
684
752
  }
685
753
  case "file":
686
754
  return null;
755
+ case "map":
756
+ return /* @__PURE__ */ new Map();
757
+ case "template-literal":
758
+ return "";
687
759
  case "any":
688
760
  case "unknown":
761
+ case "custom":
689
762
  case "void":
690
763
  case "never":
691
764
  case "promise":
692
- case "custom":
693
- case "template-literal":
694
- case "transform":
695
- case "map":
696
765
  case "symbol":
697
766
  case "function":
767
+ case "transform":
698
768
  return void 0;
699
769
  default:
700
770
  return ctx.unsupportedKindFallback(schema, kind);
701
771
  }
702
772
  }
703
773
 
704
- const store = /* @__PURE__ */ new WeakMap();
705
- const lists = /* @__PURE__ */ new WeakMap();
774
+ const state = crossCopyState(/* @__PURE__ */ Symbol.for("attaform:field-meta-state"), () => ({
775
+ store: /* @__PURE__ */ new WeakMap(),
776
+ lists: /* @__PURE__ */ new WeakMap(),
777
+ pathMapBuilder: null
778
+ }));
706
779
  const registry = {
707
780
  add(schema, payload) {
708
- store.set(schema, payload);
709
- const list = lists.get(schema) ?? [];
781
+ state.store.set(schema, payload);
782
+ const list = state.lists.get(schema) ?? [];
710
783
  list.push(payload);
711
- lists.set(schema, list);
784
+ state.lists.set(schema, list);
712
785
  return registry;
713
786
  },
714
787
  get(schema) {
715
- return store.get(schema);
788
+ return state.store.get(schema);
716
789
  },
717
790
  has(schema) {
718
- return store.has(schema);
791
+ return state.store.has(schema);
719
792
  },
720
793
  remove(schema) {
721
- store.delete(schema);
722
- lists.delete(schema);
794
+ state.store.delete(schema);
795
+ state.lists.delete(schema);
723
796
  return registry;
724
797
  }
725
798
  };
726
799
  const fieldMetaStore = registry;
727
800
  function getFieldMetaForSchema(schema) {
728
- return store.get(schema);
801
+ return state.store.get(schema);
729
802
  }
730
803
  function getFieldMetaListForSchema(schema) {
731
- return lists.get(schema) ?? [];
804
+ return state.lists.get(schema) ?? [];
732
805
  }
733
- let pathMapBuilder = null;
734
806
  function installFieldMetaPathMapBuilder(builder) {
735
- pathMapBuilder = builder;
807
+ state.pathMapBuilder = builder;
736
808
  }
737
809
  function buildFieldMetaPathMap(rootSchema, services) {
738
- return pathMapBuilder === null ? void 0 : pathMapBuilder(rootSchema, services);
810
+ const builder = state.pathMapBuilder;
811
+ return builder === null ? void 0 : builder(rootSchema, services);
739
812
  }
740
813
 
741
814
  const PERMISSIVE_SLIM_KINDS = /* @__PURE__ */ new Set([
@@ -764,6 +837,16 @@ const KIND_UNDEFINED = /* @__PURE__ */ new Set(["undefined"]);
764
837
  const KIND_OBJECT = /* @__PURE__ */ new Set(["object"]);
765
838
  const KIND_ARRAY = /* @__PURE__ */ new Set(["array"]);
766
839
  const KIND_SET = /* @__PURE__ */ new Set(["set"]);
840
+ const KIND_MAP = /* @__PURE__ */ new Set(["map"]);
841
+ const KIND_SYMBOL = /* @__PURE__ */ new Set(["symbol", "undefined"]);
842
+ const KIND_FUNCTION = /* @__PURE__ */ new Set([
843
+ "function",
844
+ "undefined"
845
+ ]);
846
+ const KIND_PROMISE = /* @__PURE__ */ new Set([
847
+ "object",
848
+ "undefined"
849
+ ]);
767
850
  const KIND_FILE = /* @__PURE__ */ new Set(["file", "null"]);
768
851
  const EMPTY_KINDS = /* @__PURE__ */ new Set();
769
852
  function slimPrimitivesWalk(schema, intro, maxDepth, lazyDepth = 0) {
@@ -820,6 +903,16 @@ function slimPrimitivesWalk(schema, intro, maxDepth, lazyDepth = 0) {
820
903
  return KIND_ARRAY;
821
904
  case "set":
822
905
  return KIND_SET;
906
+ case "map":
907
+ return KIND_MAP;
908
+ case "symbol":
909
+ return KIND_SYMBOL;
910
+ case "function":
911
+ return KIND_FUNCTION;
912
+ case "promise":
913
+ return KIND_PROMISE;
914
+ case "template-literal":
915
+ return KIND_STRING;
823
916
  case "optional": {
824
917
  const inner = intro.unwrapInner(schema);
825
918
  const innerSet = inner === void 0 ? EMPTY_KINDS : slimPrimitivesWalk(inner, intro, maxDepth, lazyDepth);
@@ -883,14 +976,19 @@ function slimPrimitivesWalk(schema, intro, maxDepth, lazyDepth = 0) {
883
976
  }
884
977
  case "never":
885
978
  return EMPTY_KINDS;
979
+ // Opaque leaves: the schema says nothing about the value's shape,
980
+ // so every kind is admissible. `custom` is the kind
981
+ // `z.instanceof(X)` and `z.custom<T>()` compile to on v4 (#542);
982
+ // it belongs with `any` / `unknown` rather than in the defensive
983
+ // fallthrough, because it reaches here through the public surface.
886
984
  case "any":
887
985
  case "unknown":
986
+ case "custom":
888
987
  return PERMISSIVE_SLIM_KINDS;
889
- // Opaque / unsupported kinds: be permissive so legitimate writes
890
- // aren't false-rejected. The unsupported kinds (`map` / `symbol` /
891
- // `function` / `promise`) are rejected at adapter construction by
892
- // `assertSupportedKinds`; this fallthrough keeps the walker
893
- // defensive in case construction is skipped.
988
+ // A kind this walker has no case for — in practice a kind a newer
989
+ // Zod introduced. Be permissive rather than reject: the adapter
990
+ // carries the value opaquely and the schema's own parse is what
991
+ // decides whether it was legal.
894
992
  default:
895
993
  return PERMISSIVE_SLIM_KINDS;
896
994
  }
@@ -984,11 +1082,20 @@ function walkForMeta(schema, path, map, counters, lastPathPerSchema, inProgress,
984
1082
  case "set": {
985
1083
  const inner = intro.getSetValueType(schema);
986
1084
  if (inner !== void 0)
987
- walkForMeta(inner, [...path, 0], map, counters, lastPathPerSchema, inProgress, services);
1085
+ walkForMeta(
1086
+ inner,
1087
+ [...path, SET_MEMBER_SEGMENT],
1088
+ map,
1089
+ counters,
1090
+ lastPathPerSchema,
1091
+ inProgress,
1092
+ services
1093
+ );
988
1094
  return;
989
1095
  }
990
- case "record": {
991
- const inner = intro.getRecordValueType(schema);
1096
+ case "record":
1097
+ case "map": {
1098
+ const inner = kind === "map" ? intro.getMapValueType(schema) : intro.getRecordValueType(schema);
992
1099
  if (inner !== void 0)
993
1100
  walkForMeta(inner, [...path, "*"], map, counters, lastPathPerSchema, inProgress, services);
994
1101
  return;
@@ -1,4 +1,4 @@
1
- import { f as pathsEqual, i as isPathPrefix } from './attaform.wfY8XFvm.mjs';
1
+ import { m as mapSegmentKeys, f as pathsEqual, i as isPathPrefix } from './attaform-dev.A-TpJW0B.mjs';
2
2
 
3
3
  const DEFAULT_FIELD_VALIDATION_DEBOUNCE_MS = 0;
4
4
  const DEFAULT_HISTORY_MAX_SNAPSHOTS = 128;
@@ -10,6 +10,12 @@ function normalizeNumericOption(config) {
10
10
  const { value, source, allowInfinity, min, defaultValue } = config;
11
11
  if (allowInfinity && value === Infinity) return Infinity;
12
12
  if (typeof value !== "number" || Number.isNaN(value) || value === Infinity || value === -Infinity) {
13
+ {
14
+ const acceptedDescription = allowInfinity ? "a non-negative integer or Infinity" : "a non-negative finite integer";
15
+ console.warn(
16
+ `[attaform] ${source} must be ${acceptedDescription}; got ${String(value)}. Falling back to ${String(defaultValue)}.`
17
+ );
18
+ }
13
19
  return defaultValue;
14
20
  }
15
21
  return Math.max(min, Math.floor(value));
@@ -22,6 +28,60 @@ function pickDefined(bag) {
22
28
  return out;
23
29
  }
24
30
 
31
+ const reported = /* @__PURE__ */ new Set() ;
32
+ function report(site, err) {
33
+ if (reported === null || reported.has(site)) return;
34
+ reported.add(site);
35
+ const advice = site === "default-factory" ? "a `.default(() => ...)` factory threw. Attaform used `undefined` for that field's initial value." : site === "catch-factory" ? "a `.catch(() => ...)` fallback threw. Attaform used `undefined` for that value." : "a `z.lazy(() => ...)` factory threw. Attaform stopped descending at that node, so paths below it will not resolve.";
36
+ console.error(
37
+ `[attaform] ${advice} A function inside your schema must not throw; wrap your own try/catch if the failure is recoverable. Original error:`,
38
+ err
39
+ );
40
+ }
41
+ function callConsumerSchemaFn(fn, fallback, site) {
42
+ try {
43
+ return fn();
44
+ } catch (err) {
45
+ report(site, err);
46
+ return fallback;
47
+ }
48
+ }
49
+ function readConsumerProp(obj, key) {
50
+ try {
51
+ return obj[key];
52
+ } catch {
53
+ return void 0;
54
+ }
55
+ }
56
+ function consumerKeys(obj) {
57
+ try {
58
+ return Object.keys(obj);
59
+ } catch {
60
+ return [];
61
+ }
62
+ }
63
+ function readConsumerIndex(arr, i) {
64
+ try {
65
+ return arr[i];
66
+ } catch {
67
+ return void 0;
68
+ }
69
+ }
70
+ function consumerSymbolKeys(obj) {
71
+ try {
72
+ return Object.getOwnPropertySymbols(obj);
73
+ } catch {
74
+ return [];
75
+ }
76
+ }
77
+ function consumerHas(obj, key) {
78
+ try {
79
+ return key in obj;
80
+ } catch {
81
+ return false;
82
+ }
83
+ }
84
+
25
85
  function safeAssign(target, key, value) {
26
86
  if (key === "__proto__") {
27
87
  Object.defineProperty(target, key, {
@@ -41,17 +101,42 @@ function safeOwnRead(target, key) {
41
101
  if (isShadowedKey(key)) {
42
102
  const desc = Object.getOwnPropertyDescriptor(target, key);
43
103
  if (desc === void 0) return void 0;
44
- return "value" in desc ? desc.value : target[key];
104
+ return "value" in desc ? desc.value : readConsumerProp(target, key);
45
105
  }
46
- return target[key];
106
+ return readConsumerProp(target, key);
47
107
  }
48
108
  function safeOwnHas(target, key) {
49
- return Object.prototype.hasOwnProperty.call(target, key);
109
+ try {
110
+ return Object.prototype.hasOwnProperty.call(target, key);
111
+ } catch {
112
+ return false;
113
+ }
114
+ }
115
+ function spreadConsumerRecord(src) {
116
+ try {
117
+ return { ...src };
118
+ } catch {
119
+ const out = {};
120
+ for (const key of Object.keys(src)) {
121
+ safeAssign(out, key, readConsumerProp(src, key));
122
+ }
123
+ return out;
124
+ }
125
+ }
126
+ function copyConsumerArray(src) {
127
+ try {
128
+ return src.slice();
129
+ } catch {
130
+ const out = new Array(src.length);
131
+ for (let i = 0; i < src.length; i++) out[i] = readConsumerIndex(src, i);
132
+ return out;
133
+ }
50
134
  }
51
135
 
52
136
  function isDescendable(value) {
53
137
  if (value === null || typeof value !== "object") return false;
54
138
  if (Array.isArray(value)) return true;
139
+ if (value instanceof Map) return mapSegmentKeys(value) !== null;
55
140
  const proto = Object.getPrototypeOf(value);
56
141
  return proto === null || proto === Object.prototype;
57
142
  }
@@ -77,6 +162,16 @@ function diffAndApply(oldValue, newValue, prefix, visit) {
77
162
  return;
78
163
  }
79
164
  if (oldIsDescendable && newIsDescendable) {
165
+ const oldIsMap = oldValue instanceof Map;
166
+ const newIsMap = newValue instanceof Map;
167
+ if (oldIsMap && newIsMap) {
168
+ diffMapsLockstep(oldValue, newValue, prefix, visit);
169
+ return;
170
+ }
171
+ if (oldIsMap !== newIsMap) {
172
+ visit({ kind: "changed", path: prefix, oldValue, newValue });
173
+ return;
174
+ }
80
175
  const oldIsArray = Array.isArray(oldValue);
81
176
  const newIsArray = Array.isArray(newValue);
82
177
  if (oldIsArray && newIsArray) {
@@ -116,46 +211,79 @@ function diffAndApply(oldValue, newValue, prefix, visit) {
116
211
  function walkNewDescendable(newValue, prefix, visit) {
117
212
  if (Array.isArray(newValue)) {
118
213
  for (let i = 0; i < newValue.length; i++) {
119
- diffAndApply(void 0, newValue[i], appendSegment(prefix, i), visit);
214
+ diffAndApply(void 0, readConsumerIndex(newValue, i), appendSegment(prefix, i), visit);
215
+ }
216
+ } else if (newValue instanceof Map) {
217
+ for (const [key, entry] of newValue) {
218
+ diffAndApply(void 0, entry, appendSegment(prefix, key), visit);
120
219
  }
121
220
  } else {
122
221
  const rec = newValue;
123
- for (const k of Object.keys(rec)) {
124
- diffAndApply(void 0, rec[k], appendSegment(prefix, k), visit);
222
+ for (const k of consumerKeys(rec)) {
223
+ diffAndApply(void 0, readConsumerProp(rec, k), appendSegment(prefix, k), visit);
125
224
  }
126
225
  }
127
226
  }
128
227
  function walkOldDescendable(oldValue, prefix, visit) {
129
228
  if (Array.isArray(oldValue)) {
130
229
  for (let i = 0; i < oldValue.length; i++) {
131
- diffAndApply(oldValue[i], void 0, appendSegment(prefix, i), visit);
230
+ diffAndApply(readConsumerIndex(oldValue, i), void 0, appendSegment(prefix, i), visit);
231
+ }
232
+ } else if (oldValue instanceof Map) {
233
+ for (const [key, entry] of oldValue) {
234
+ diffAndApply(entry, void 0, appendSegment(prefix, key), visit);
132
235
  }
133
236
  } else {
134
237
  const rec = oldValue;
135
- for (const k of Object.keys(rec)) {
136
- diffAndApply(rec[k], void 0, appendSegment(prefix, k), visit);
238
+ for (const k of consumerKeys(rec)) {
239
+ diffAndApply(readConsumerProp(rec, k), void 0, appendSegment(prefix, k), visit);
137
240
  }
138
241
  }
139
242
  }
243
+ function diffMapsLockstep(oldMap, newMap, prefix, visit) {
244
+ for (const [key, entry] of newMap) {
245
+ diffAndApply(oldMap.get(key), entry, appendSegment(prefix, key), visit);
246
+ }
247
+ for (const [key, entry] of oldMap) {
248
+ if (newMap.has(key)) continue;
249
+ diffAndApply(entry, void 0, appendSegment(prefix, key), visit);
250
+ }
251
+ }
140
252
  function diffArraysLockstep(oldArr, newArr, prefix, visit) {
141
253
  const max = Math.max(oldArr.length, newArr.length);
142
254
  for (let i = 0; i < max; i++) {
143
- diffAndApply(oldArr[i], newArr[i], appendSegment(prefix, i), visit);
255
+ diffAndApply(
256
+ readConsumerIndex(oldArr, i),
257
+ readConsumerIndex(newArr, i),
258
+ appendSegment(prefix, i),
259
+ visit
260
+ );
144
261
  }
145
262
  }
146
263
  function diffObjectsLockstep(oldRec, newRec, prefix, visit) {
147
264
  const seen = /* @__PURE__ */ new Set();
148
- for (const k of Object.keys(oldRec)) {
265
+ for (const k of consumerKeys(oldRec)) {
149
266
  seen.add(k);
150
- diffAndApply(oldRec[k], newRec[k], appendSegment(prefix, k), visit);
267
+ diffAndApply(
268
+ readConsumerProp(oldRec, k),
269
+ readConsumerProp(newRec, k),
270
+ appendSegment(prefix, k),
271
+ visit
272
+ );
151
273
  }
152
- for (const k of Object.keys(newRec)) {
274
+ for (const k of consumerKeys(newRec)) {
153
275
  if (seen.has(k)) continue;
154
- diffAndApply(oldRec[k], newRec[k], appendSegment(prefix, k), visit);
276
+ diffAndApply(
277
+ readConsumerProp(oldRec, k),
278
+ readConsumerProp(newRec, k),
279
+ appendSegment(prefix, k),
280
+ visit
281
+ );
155
282
  }
156
283
  }
157
284
  function applyChangedKeys(target, source, arrayOpPath, currentPath, patches) {
158
285
  if (!isDescendable(target) || !isDescendable(source)) return false;
286
+ if (target instanceof Map || source instanceof Map) return false;
159
287
  const targetIsArray = Array.isArray(target);
160
288
  const sourceIsArray = Array.isArray(source);
161
289
  if (targetIsArray !== sourceIsArray) return false;
@@ -224,6 +352,11 @@ function applyChangedKeys(target, source, arrayOpPath, currentPath, patches) {
224
352
  }
225
353
  function structuralSnapshot(value) {
226
354
  if (!isDescendable(value)) return value;
355
+ if (value instanceof Map) {
356
+ const out2 = /* @__PURE__ */ new Map();
357
+ for (const [k, v] of value) out2.set(k, structuralSnapshot(v));
358
+ return out2;
359
+ }
227
360
  if (Array.isArray(value)) {
228
361
  const out2 = new Array(value.length);
229
362
  for (let i = 0; i < value.length; i++) {
@@ -239,4 +372,4 @@ function structuralSnapshot(value) {
239
372
  return out;
240
373
  }
241
374
 
242
- export { ANONYMOUS_FORM_KEY_PREFIX as A, DEFAULT_HISTORY_MAX_SNAPSHOTS as D, RESERVED_KEY_PREFIX as R, safeOwnRead as a, safeAssign as b, safeOwnHas as c, diffAndApply as d, DEFAULT_FIELD_VALIDATION_DEBOUNCE_MS as e, applyChangedKeys as f, DEFAULT_MAX_RECURSION_DEPTH as g, ANONYMOUS_WIZARD_KEY_PREFIX as h, isShadowedKey as i, normalizeNumericOption as n, pickDefined as p, structuralSnapshot as s };
375
+ export { ANONYMOUS_FORM_KEY_PREFIX as A, DEFAULT_HISTORY_MAX_SNAPSHOTS as D, RESERVED_KEY_PREFIX as R, safeOwnRead as a, safeAssign as b, callConsumerSchemaFn as c, consumerHas as d, safeOwnHas as e, spreadConsumerRecord as f, copyConsumerArray as g, consumerKeys as h, isShadowedKey as i, readConsumerProp as j, diffAndApply as k, DEFAULT_FIELD_VALIDATION_DEBOUNCE_MS as l, consumerSymbolKeys as m, normalizeNumericOption as n, applyChangedKeys as o, pickDefined as p, DEFAULT_MAX_RECURSION_DEPTH as q, readConsumerIndex as r, structuralSnapshot as s, ANONYMOUS_WIZARD_KEY_PREFIX as t };
@@ -24,6 +24,14 @@ function canonicalStringify(value, seen = /* @__PURE__ */ new WeakSet()) {
24
24
  try {
25
25
  if (value instanceof Date) return `date:${value.getTime()}`;
26
26
  if (value instanceof RegExp) return `regex:${String(value)}`;
27
+ if (value instanceof Map) {
28
+ const entries2 = [...value].map(([k, v]) => `${canonicalStringify(k, seen)}=>${canonicalStringify(v, seen)}`).sort();
29
+ return `map:[${entries2.join(",")}]`;
30
+ }
31
+ if (value instanceof Set) {
32
+ const members = [...value].map((v) => canonicalStringify(v, seen)).sort();
33
+ return `set:[${members.join(",")}]`;
34
+ }
27
35
  const entries = Object.entries(obj).sort(([a], [b]) => a < b ? -1 : a > b ? 1 : 0).map(([k, v]) => `${JSON.stringify(k)}:${canonicalStringify(v, seen)}`);
28
36
  return `{${entries.join(",")}}`;
29
37
  } finally {
@@ -1,5 +1,5 @@
1
1
  import { reactive, markRaw, isRef, effectScope, watch, warn, nextTick } from 'vue';
2
- import { e as canonicalizePath } from './attaform-dev.Dr2YzS5B.mjs';
2
+ import { e as canonicalizePath } from './attaform-dev.A-TpJW0B.mjs';
3
3
 
4
4
  const INTERACTIVE_TAG_NAMES = /* @__PURE__ */ new Set(["INPUT", "SELECT", "TEXTAREA"]);
5
5
 
@@ -1143,6 +1143,14 @@ function setSelected(el, value) {
1143
1143
  const externalValue = value.innerRef.value;
1144
1144
  const isMultiple = el.multiple;
1145
1145
  const isArrayValue = isArray(externalValue);
1146
+ const isUnset = externalValue === null || externalValue === void 0;
1147
+ if (isMultiple && isUnset) {
1148
+ for (let i = 0, l = el.options.length; i < l; i++) {
1149
+ const option = el.options[i];
1150
+ if (option !== void 0) option.selected = false;
1151
+ }
1152
+ return;
1153
+ }
1146
1154
  if (isMultiple && !isArrayValue && !isSet(externalValue)) {
1147
1155
  {
1148
1156
  warn(
@@ -1180,10 +1188,11 @@ function setSelected(el, value) {
1180
1188
  }
1181
1189
  return;
1182
1190
  }
1191
+ const target = value.displayValue.value === "" ? "" : externalValue;
1183
1192
  for (let i = 0, l = el.options.length; i < l; i++) {
1184
1193
  const option = el.options[i];
1185
1194
  if (!option) continue;
1186
- if (looseEqual(applyCoerce(getValue(option), value), externalValue)) {
1195
+ if (looseEqual(applyCoerce(getValue(option), value), target)) {
1187
1196
  if (el.selectedIndex !== i) el.selectedIndex = i;
1188
1197
  return;
1189
1198
  }
@@ -1269,8 +1278,7 @@ function observeForLateHostControl(el, rv) {
1269
1278
  hostHealObservers.set(el, observer);
1270
1279
  }
1271
1280
  function activateComponentHost(el, rv) {
1272
- if (rv.hasRegisteredDescendant(el))
1273
- return;
1281
+ if (rv.hasRegisteredDescendant(el)) return;
1274
1282
  el[REGISTER_OWNER_MARKER] = true;
1275
1283
  if (!el.tagName.includes("-")) {
1276
1284
  el.removeAttribute("registerValue");
@@ -1394,6 +1402,7 @@ function resolveDynamicModel(tagName, type) {
1394
1402
  function warnRedundantStateBinding(el, binding, vnode) {
1395
1403
  if (warnedRedundantBindings === null) return;
1396
1404
  if (!INTERACTIVE_TAG_NAMES.has(el.tagName)) return;
1405
+ if (!isRegisterValue(binding.value)) return;
1397
1406
  if (binding.modifiers[V_REGISTER_COMPILED_MODIFIER] === true) return;
1398
1407
  const props = vnode.props;
1399
1408
  if (props == null) return;
@@ -1,4 +1,4 @@
1
- import { c as RegistryNotInstalledError, O as OutsideSetupError, g as pathKeyToDotted } from './attaform-dev.Dr2YzS5B.mjs';
1
+ import { c as RegistryNotInstalledError, O as OutsideSetupError, g as pathKeyToDotted } from './attaform-dev.A-TpJW0B.mjs';
2
2
  import { shallowReactive, getCurrentInstance, inject } from 'vue';
3
3
 
4
4
  function detectSSR(options = {}) {