@shivaedev/form 0.7.0 → 0.8.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/CHANGELOG.md CHANGED
@@ -1,5 +1,28 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.8.0 - 2026-10-30
4
+
5
+ ### Fixed
6
+
7
+ - Work Board reads draft timestamps and expiry through its form client’s runtime Clock.
8
+
9
+ ### Breaking
10
+
11
+ - Persisted drafts require a `now: () => number` callback in core forms, `usePersistedDraft`, `useEditor` and `useCreate`. Capture `Clock.Clock` in the application’s Effect setup and pass `now: () => clock.currentTimeMillisUnsafe()` so timestamps and expiry follow that clock, including TestClock in stories.
12
+ - Form no longer exports the identity cast helpers `holder`, `fieldOf`, `choicesOf` or `checkOf` from `shape.ts`, or `keySelector` from `paths.ts`. Use declared reference, field, check and selector types directly; get field refs and choices through the form’s typed `field` and `choices` methods.
13
+
14
+ ## 0.7.1 - 2026-10-30
15
+
16
+ ### Changed
17
+
18
+ - Require Effect 4.0.6 and align the Effect companion package peers and generated starter catalog to the same exact release. Install the 4.0.6 Effect stack together.
19
+
20
+ ### Fixed
21
+
22
+ - Register hosted RPC cache-control handling through Effect 4.0.6's request-scoped pre-response API so responses keep `private, no-store`.
23
+ - Accept native RPC's `application/x-ndjson` media type while preserving `application/ndjson` callers at the transport guard.
24
+ - Keep subscriptions open after their HTTP request body completes; closing the socket still cancels them.
25
+
3
26
  ## 0.7.0 - 2026-10-27
4
27
 
5
28
  ### Breaking
package/README.md CHANGED
@@ -8,9 +8,9 @@ An input gives you a string; your service needs a number. Meanwhile, fresh serve
8
8
 
9
9
  ```ts
10
10
  const order = form(Schema.Struct({ name: Schema.String, quantity: Schema.NumberFromString }), {
11
- initialValues: { name: "Paper", quantity: "300" },
12
- onSubmit: Effect.succeed,
13
- runtime,
11
+ initialValues: { name: "Paper", quantity: "300" },
12
+ onSubmit: Effect.succeed,
13
+ runtime,
14
14
  });
15
15
 
16
16
  order.change("name", "Copy paper");
@@ -45,32 +45,27 @@ import { form } from "@shivaedev/form/form.ts";
45
45
 
46
46
  const runtime = Atom.runtime(Layer.empty);
47
47
  const fields = Schema.Struct({
48
- name: Schema.NonEmptyString,
49
- quantity: Schema.NumberFromString,
48
+ name: Schema.NonEmptyString,
49
+ quantity: Schema.NumberFromString,
50
50
  });
51
51
 
52
52
  const order = form(fields, {
53
- initialValues: { name: "Paper", quantity: "300" },
54
- onSubmit: (values, submitter) =>
55
- values.name === "reserved"
56
- ? submitter.fail("name", "Choose another name")
57
- : Effect.succeed(values),
58
- runtime,
53
+ initialValues: { name: "Paper", quantity: "300" },
54
+ onSubmit: (values, submitter) => (values.name === "reserved" ? submitter.fail("name", "Choose another name") : Effect.succeed(values)),
55
+ runtime,
59
56
  });
60
57
 
61
58
  const registry = AtomRegistry.make();
62
59
  const release = registry.mount(order.dirty);
63
60
 
64
61
  try {
65
- order.change("quantity", "350");
66
- registry.set(order.submit, undefined);
67
- const saved = await Effect.runPromise(
68
- AtomRegistry.getResult(registry, order.submit, { suspendOnWaiting: true }),
69
- );
70
- console.log(saved);
62
+ order.change("quantity", "350");
63
+ registry.set(order.submit, undefined);
64
+ const saved = await Effect.runPromise(AtomRegistry.getResult(registry, order.submit, { suspendOnWaiting: true }));
65
+ console.log(saved);
71
66
  } finally {
72
- release();
73
- registry.dispose();
67
+ release();
68
+ registry.dispose();
74
69
  }
75
70
  ```
76
71
 
@@ -94,40 +89,54 @@ const runtime = Atom.runtime(Layer.empty);
94
89
  const fields = Schema.Struct({ name: Schema.NonEmptyString, quantity: Schema.NumberFromString });
95
90
 
96
91
  function OrderEditor() {
97
- const [order] = useState(() => form(fields, {
98
- initialValues: { name: "Paper", quantity: "300" },
99
- onSubmit: Effect.succeed,
100
- runtime,
101
- }));
102
- const name = useField(order, "name");
103
- const quantity = useField(order, "quantity");
104
- const submit = useSubmit(order);
105
- const dirty = useDirty(order);
106
-
107
- return <form onSubmit={(event) => {
108
- event.preventDefault();
109
- if (!submit.submitting) submit.run();
110
- }}>
111
- <label>Name <input value={name.value} onBlur={name.onBlur}
112
- onChange={(event) => name.onChange(event.target.value)} /></label>
113
- {name.error && <p role="alert">{name.error}</p>}
114
- <label>Quantity <input value={quantity.value} onBlur={quantity.onBlur}
115
- onChange={(event) => quantity.onChange(event.target.value)} /></label>
116
- {quantity.error && <p role="alert">{quantity.error}</p>}
117
- <button disabled={submit.submitting}>Save</button>
118
- <button type="button" onClick={order.revert}>Revert</button>
119
- <p role="status">{submit.submitting ? "Saving…" : dirty ? "Unsaved changes" : "Saved"}</p>
120
- </form>;
92
+ const [order] = useState(() =>
93
+ form(fields, {
94
+ initialValues: { name: "Paper", quantity: "300" },
95
+ onSubmit: Effect.succeed,
96
+ runtime,
97
+ }),
98
+ );
99
+ const name = useField(order, "name");
100
+ const quantity = useField(order, "quantity");
101
+ const submit = useSubmit(order);
102
+ const dirty = useDirty(order);
103
+
104
+ return (
105
+ <form
106
+ onSubmit={(event) => {
107
+ event.preventDefault();
108
+ if (!submit.submitting) submit.run();
109
+ }}
110
+ >
111
+ <label>
112
+ Name <input value={name.value} onBlur={name.onBlur} onChange={(event) => name.onChange(event.target.value)} />
113
+ </label>
114
+ {name.error && <p role="alert">{name.error}</p>}
115
+ <label>
116
+ Quantity <input value={quantity.value} onBlur={quantity.onBlur} onChange={(event) => quantity.onChange(event.target.value)} />
117
+ </label>
118
+ {quantity.error && <p role="alert">{quantity.error}</p>}
119
+ <button disabled={submit.submitting}>Save</button>
120
+ <button type="button" onClick={order.revert}>
121
+ Revert
122
+ </button>
123
+ <p role="status">{submit.submitting ? "Saving…" : dirty ? "Unsaved changes" : "Saved"}</p>
124
+ </form>
125
+ );
121
126
  }
122
127
 
123
128
  export function mountOrderEditor(container: HTMLElement) {
124
- const registry = AtomRegistry.make();
125
- const root = createRoot(container);
126
- root.render(<RegistryContext.Provider value={registry}><OrderEditor /></RegistryContext.Provider>);
127
- return () => {
128
- root.unmount();
129
- registry.dispose();
130
- };
129
+ const registry = AtomRegistry.make();
130
+ const root = createRoot(container);
131
+ root.render(
132
+ <RegistryContext.Provider value={registry}>
133
+ <OrderEditor />
134
+ </RegistryContext.Provider>,
135
+ );
136
+ return () => {
137
+ root.unmount();
138
+ registry.dispose();
139
+ };
131
140
  }
132
141
  ```
133
142
 
@@ -139,16 +148,16 @@ Render general submission failures from `submit.result` in the application's own
139
148
 
140
149
  Call `receive` with encoded values from a refreshed or saved row. Encode domain values before receiving them; for a numeric string field, receive `String(row.quantity)`.
141
150
 
142
- | Situation | What the form does |
143
- | --- | --- |
144
- | A field still equals its baseline | Receives the new value. |
145
- | A field was edited locally | Keeps that input; received values become the new baseline. |
146
- | A refresh omits an untouched optional key | Removes the key. |
147
- | An optional key was added locally | Keeps it when a refresh omits it; revert restores the received values. |
148
- | The handler succeeds | Accepts the submitted encoded values without replacing later edits. |
151
+ | Situation | What the form does |
152
+ | ------------------------------------------ | ---------------------------------------------------------------------------------------------------------------------------- |
153
+ | A field still equals its baseline | Receives the new value. |
154
+ | A field was edited locally | Keeps that input; received values become the new baseline. |
155
+ | A refresh omits an untouched optional key | Removes the key. |
156
+ | An optional key was added locally | Keeps it when a refresh omits it; revert restores the received values. |
157
+ | The handler succeeds | Accepts the submitted encoded values without replacing later edits. |
149
158
  | A refresh arrived during a successful save | Keeps that refresh as the baseline; values still equal to the accepted submission count as saved and adopt the next refresh. |
150
- | The handler fails | Keeps input; an intervening refresh remains the baseline. |
151
- | `revert()` is called | Restores the latest baseline, including omitted optional keys. |
159
+ | The handler fails | Keeps input; an intervening refresh remains the baseline. |
160
+ | `revert()` is called | Restores the latest baseline, including omitted optional keys. |
152
161
 
153
162
  The form does not replace submitted encoded input with its decoded representation. A trimmed name can be accepted as saved while the input still contains its spaces. Receive the normalized saved row when the application wants that representation on screen. `useEditor` from `react` performs that composition.
154
163
 
@@ -156,14 +165,16 @@ The form does not replace submitted encoded input with its decoded representatio
156
165
 
157
166
  Opt in with `persistedDraft`. The application chooses a key for one logical editing session. Keep that key stable across server revisions so a refresh can find the same draft; choose a new key when the encoded field shape changes. Stored input includes its baseline and edited field names, so edited fields survive reload while untouched fields adopt the latest received values.
158
167
 
159
- For a core form, supply the storage provider explicitly:
168
+ Supply `now`, a function that reads epoch milliseconds from the caller’s clock. Capture `Clock.Clock` in the application’s Effect setup and pass its `currentTimeMillisUnsafe` method through a closure. The same callback reads time on each write and expiry check, so a supplied TestClock controls draft age. For a core form, supply the storage provider explicitly:
160
169
 
161
170
  ```ts
171
+ const clock = yield* Clock.Clock;
172
+ const now = () => clock.currentTimeMillisUnsafe();
162
173
  const order = form(fields, {
163
- initialValues: { name: "Paper", quantity: "300" },
164
- onSubmit: Effect.succeed,
165
- persistedDraft: { key: "order:123", storage: () => window.localStorage },
166
- runtime,
174
+ initialValues: { name: "Paper", quantity: "300" },
175
+ onSubmit: Effect.succeed,
176
+ persistedDraft: { key: "order:123", now, storage: () => window.localStorage },
177
+ runtime,
167
178
  });
168
179
  ```
169
180
 
@@ -173,19 +184,21 @@ For a React form, call `usePersistedDraft` before creating the form. It defaults
173
184
  import { useState } from "react";
174
185
  import { usePersistedDraft } from "@shivaedev/form/client/react.ts";
175
186
 
176
- function OrderEditor() {
177
- const persistedDraft = usePersistedDraft({ key: "order:123" });
178
- const [order] = useState(() => form(fields, {
179
- initialValues: { name: "Paper", quantity: "300" },
180
- onSubmit: Effect.succeed,
181
- persistedDraft,
182
- runtime,
183
- }));
184
- return <OrderFields form={form} />;
187
+ function OrderEditor({ now }: { readonly now: () => number }) {
188
+ const persistedDraft = usePersistedDraft({ key: "order:123", now });
189
+ const [order] = useState(() =>
190
+ form(fields, {
191
+ initialValues: { name: "Paper", quantity: "300" },
192
+ onSubmit: Effect.succeed,
193
+ persistedDraft,
194
+ runtime,
195
+ }),
196
+ );
197
+ return <OrderFields form={order} />;
185
198
  }
186
199
  ```
187
200
 
188
- `OrderFields` is the application's field UI. Keep this component mounted for one record; remount it when its identity changes. `useEditor` and `useCreate` from `react` accept `persistedDraft: { key }` directly and attach the same owner. A committed `SessionBoundary` session replacement or sign-out drops its tracked drafts, including screens already unmounted, and disables writes from its old forms. A suspended replacement that is canceled preserves the visible session's stored draft and future persistence. Ordinary unmounts and React effect replay preserve stored drafts. A stored draft with a different session generation is discarded when read.
201
+ `OrderFields` is the application's field UI. Keep this component mounted for one record; remount it when its identity changes. `useEditor` and `useCreate` from `react` accept `persistedDraft: { key, now }` directly and attach the same owner. A committed `SessionBoundary` session replacement or sign-out drops its tracked drafts, including screens already unmounted, and disables writes from its old forms. A suspended replacement that is canceled preserves the visible session's stored draft and future persistence. Ordinary unmounts and React effect replay preserve stored drafts. A stored draft with a different session generation is discarded when read.
189
202
 
190
203
  Each stored record defaults to at most 256 KiB of UTF-8 JSON and seven days since its last write. Set `maxBytes` and `maxAgeMs` to finite positive limits to change those bounds. Oversized, expired, malformed or incompatible records are dropped when encountered. Persistence requires JSON-compatible encoded input; invalid input such as an empty required string or an unfinished numeric string still persists. Storage access, serialization and quota failures leave the form usable.
191
204
 
@@ -201,13 +214,13 @@ For `Schema.NonEmptyString`, an empty input's message is `Required`. Longer mini
201
214
 
202
215
  ```ts
203
216
  const profile = form(Schema.Struct({ name: Schema.String }), {
204
- checks: {
205
- name: (value) => Effect.succeed(value === "taken" ? "Name is taken" : undefined),
206
- },
207
- debounce: "300 millis",
208
- initialValues: { name: "" },
209
- onSubmit: Effect.succeed,
210
- runtime,
217
+ checks: {
218
+ name: (value) => Effect.succeed(value === "taken" ? "Name is taken" : undefined),
219
+ },
220
+ debounce: "300 millis",
221
+ initialValues: { name: "" },
222
+ onSubmit: Effect.succeed,
223
+ runtime,
211
224
  });
212
225
  ```
213
226
 
@@ -220,15 +233,17 @@ For a nested value held in one top-level field, `errorAt(["answers", index, "tex
220
233
  Pass a path tuple to `submitter.fail` to reject one element or a property inside it. Paths use indices in the submitted encoded snapshot. Optional `arrayKeys` selectors receive encoded elements of top-level array fields and return their stable, unique keys:
221
234
 
222
235
  ```ts
223
- const answers = form(Schema.Struct({
224
- answers: Schema.Array(Schema.Struct({ id: Schema.String, text: Schema.NonEmptyString })),
225
- }), {
226
- arrayKeys: { answers: answer => answer.id },
227
- initialValues: { answers: [{ id: "question", text: "Yes" }] },
228
- onSubmit: (_values, submitter) =>
229
- submitter.fail(["answers", 0, "text"], "This answer is closed"),
230
- runtime,
231
- });
236
+ const answers = form(
237
+ Schema.Struct({
238
+ answers: Schema.Array(Schema.Struct({ id: Schema.String, text: Schema.NonEmptyString })),
239
+ }),
240
+ {
241
+ arrayKeys: { answers: (answer) => answer.id },
242
+ initialValues: { answers: [{ id: "question", text: "Yes" }] },
243
+ onSubmit: (_values, submitter) => submitter.fail(["answers", 0, "text"], "This answer is closed"),
244
+ runtime,
245
+ },
246
+ );
232
247
  ```
233
248
 
234
249
  `FieldFailure.path` keeps the top-level field name as a string. For a tuple rejection, optional `FieldFailure.segments` contains its submitted path.
@@ -244,8 +259,8 @@ import { Schema } from "effect";
244
259
  import { emptyAsNull } from "@shivaedev/form/emptyAsNull.ts";
245
260
 
246
261
  const fields = Schema.Struct({
247
- visibility: Schema.Literals(["private", "public"]),
248
- quantity: emptyAsNull(Schema.NumberFromString),
262
+ visibility: Schema.Literals(["private", "public"]),
263
+ quantity: emptyAsNull(Schema.NumberFromString),
249
264
  });
250
265
  ```
251
266
 
@@ -255,42 +270,42 @@ For a form made with these fields, `order.choices("visibility")` returns the enc
255
270
 
256
271
  Import the module that defines a name; there is no root entry.
257
272
 
258
- | Module | Application-facing exports |
259
- | --- | --- |
260
- | `@shivaedev/form/form.ts` | `form(schema, config)` |
261
- | `@shivaedev/form/shape.ts` | `Form`, `Submitter`, `FieldFailure`, `Invalid` and the field types they use |
273
+ | Module | Application-facing exports |
274
+ | --------------------------------- | ------------------------------------------------------------------------------- |
275
+ | `@shivaedev/form/form.ts` | `form(schema, config)` |
276
+ | `@shivaedev/form/shape.ts` | `Form`, `Submitter`, `FieldFailure`, `Invalid` and the field types they use |
262
277
  | `@shivaedev/form/client/react.ts` | `useField`, `useSubmit`, `useDirty`, `usePersistedDraft`, `DraftSessionContext` |
263
- | `@shivaedev/form/draftSession.ts` | `draftSession(id)` |
264
- | `@shivaedev/form/emptyAsNull.ts` | `emptyAsNull` |
278
+ | `@shivaedev/form/draftSession.ts` | `draftSession(id)` |
279
+ | `@shivaedev/form/emptyAsNull.ts` | `emptyAsNull` |
265
280
 
266
281
  `form` takes a `Schema.Struct` and this configuration:
267
282
 
268
- | Option | Type or role |
269
- | --- | --- |
270
- | `initialValues` | `Encoded<F>` |
271
- | `runtime` | Atom runtime for the handler/check services and schema decoding services |
272
- | `onSubmit` | `(values, submitter, submitted) => Effect<A, E, R>`; the three arguments are decoded values, field failure helper and encoded snapshot |
273
- | `checks` | Optional functions keyed by field, from encoded input to an Effect of `string \| undefined` |
274
- | `arrayKeys` | Optional `ArrayKeys<F>` selectors keyed by top-level array field, from encoded element to stable `PropertyKey`; retains nested feedback across reordering |
275
- | `debounce` | Optional Effect `Duration.Input` for checks |
276
- | `persistedDraft` | Optional `{ key, storage, maxBytes?, maxAgeMs?, session? }`; React's `usePersistedDraft` supplies storage and session ownership |
283
+ | Option | Type or role |
284
+ | ---------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------- |
285
+ | `initialValues` | `Encoded<F>` |
286
+ | `runtime` | Atom runtime for the handler/check services and schema decoding services |
287
+ | `onSubmit` | `(values, submitter, submitted) => Effect<A, E, R>`; the three arguments are decoded values, field failure helper and encoded snapshot |
288
+ | `checks` | Optional functions keyed by field, from encoded input to an Effect of `string \| undefined` |
289
+ | `arrayKeys` | Optional `ArrayKeys<F>` selectors keyed by top-level array field, from encoded element to stable `PropertyKey`; retains nested feedback across reordering |
290
+ | `debounce` | Optional Effect `Duration.Input` for checks |
291
+ | `persistedDraft` | Optional `{ key, storage, maxBytes?, maxAgeMs?, session? }`; React's `usePersistedDraft` supplies storage and session ownership |
277
292
 
278
293
  The returned form exposes:
279
294
 
280
- | Member | Type or use |
281
- | --- | --- |
282
- | `values` | `AtomRef<Encoded<F>>` for the whole input |
283
- | `field(name)` | `AtomRef<Encoded<F>[K]>` for a field |
284
- | `change(name, value)` | Write encoded input through the form's editing operation |
285
- | `blur(name)` | Field blur operation, supplied as `useField(...).onBlur` |
286
- | `error(name)` | Atom of `string \| undefined` |
295
+ | Member | Type or use |
296
+ | -------------------------- | --------------------------------------------------------------------------------------------- |
297
+ | `values` | `AtomRef<Encoded<F>>` for the whole input |
298
+ | `field(name)` | `AtomRef<Encoded<F>[K]>` for a field |
299
+ | `change(name, value)` | Write encoded input through the form's editing operation |
300
+ | `blur(name)` | Field blur operation, supplied as `useField(...).onBlur` |
301
+ | `error(name)` | Atom of `string \| undefined` |
287
302
  | `errorAt([name, ...path])` | Atom of nested Schema feedback and handler rejections; visibility follows the top-level field |
288
- | `choices(name)` | Encoded choices or `undefined` |
289
- | `dirty` | Atom of `boolean` |
290
- | `receive(values)` | Merge received encoded values |
291
- | `revert()` | Restore the baseline |
292
- | `submit` | `AtomResultFn<void, A, E \| ER \| FieldFailure \| Invalid>` |
293
- | `submitting` | Atom of `boolean` for submission waiting state |
303
+ | `choices(name)` | Encoded choices or `undefined` |
304
+ | `dirty` | Atom of `boolean` |
305
+ | `receive(values)` | Merge received encoded values |
306
+ | `revert()` | Restore the baseline |
307
+ | `submit` | `AtomResultFn<void, A, E \| ER \| FieldFailure \| Invalid>` |
308
+ | `submitting` | Atom of `boolean` for submission waiting state |
294
309
 
295
310
  `F` is the schema's fields, `A` and `E` are the handler's success and failure types, and `ER` is the atom runtime's failure type. `FieldFailure` contains the top-level string `path`, `message` and optional submitted path `segments`; `Invalid` contains `messages`, a `FieldMessages` record.
296
311
 
@@ -299,17 +314,16 @@ The lower-level `draft.ts` (`draft`), `refs.ts` (`fromRef`, `propertyRef`) and `
299
314
  ### Install and limits
300
315
 
301
316
  ```sh
302
- pnpm add @shivaedev/form effect@4.0.5
317
+ pnpm add @shivaedev/form effect
303
318
  ```
304
319
 
305
320
  For React bindings:
306
321
 
307
322
  ```sh
308
- pnpm add @effect/atom-react@4.0.5 react@19.3.0
323
+ pnpm add @effect/atom-react react
309
324
  ```
310
325
 
311
326
  The React mounting example also uses the application's `react-dom`. React and `@effect/atom-react` are optional peers; the core modules do not import them. The package needs Node 24 or newer.
312
-
313
327
  - Field names are top-level schema keys. There is no path-addressed field-array API.
314
328
  - Replace encoded values rather than mutating objects in place; use `change` for ordinary UI edits.
315
329
  - Keep the form and registry for their intended session, and clean up the registry when that session ends.
package/dist/form.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { type Schema } from "effect";
1
+ import { Schema } from "effect";
2
2
  import { type Config, type Fields, type Form } from "./shape.ts";
3
3
  export declare function form<TFields extends Fields, TValue, TError, TServices, TRuntimeError>(schema: Schema.Struct<TFields>, config: Config<TFields, TValue, TError, TServices, TRuntimeError>): Form<TFields, TValue, TError, TRuntimeError>;
4
4
  //# sourceMappingURL=form.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"form.d.ts","sourceRoot":"","sources":["../src/form.ts"],"names":[],"mappings":"AAAA,OAAO,EAAyB,KAAK,MAAM,EAAkC,MAAM,QAAQ,CAAC;AAS5F,OAAO,EACN,KAAK,MAAM,EAMX,KAAK,MAAM,EACX,KAAK,IAAI,EAMT,MAAM,YAAY,CAAC;AAIpB,wBAAgB,IAAI,CAAC,OAAO,SAAS,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,aAAa,EACpF,MAAM,EAAE,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,EAC9B,MAAM,EAAE,MAAM,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,aAAa,CAAC,GAC/D,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,aAAa,CAAC,CA+G9C"}
1
+ {"version":3,"file":"form.d.ts","sourceRoot":"","sources":["../src/form.ts"],"names":[],"mappings":"AAAA,OAAO,EAAyB,MAAM,EAAkC,MAAM,QAAQ,CAAC;AASvF,OAAO,EAAE,KAAK,MAAM,EAA4C,KAAK,MAAM,EAAE,KAAK,IAAI,EAAsC,MAAM,YAAY,CAAC;AAI/I,wBAAgB,IAAI,CAAC,OAAO,SAAS,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,aAAa,EACpF,MAAM,EAAE,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,EAC9B,MAAM,EAAE,MAAM,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,aAAa,CAAC,GAC/D,IAAI,CAAC,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,aAAa,CAAC,CA6G9C"}
package/dist/form.js CHANGED
@@ -1,4 +1,4 @@
1
- import { Effect, Equal, Result, SchemaParser } from "effect";
1
+ import { Effect, Equal, Result, Schema, SchemaParser } from "effect";
2
2
  import * as AsyncResult from "effect/reactivity/AsyncResult";
3
3
  import * as Atom from "effect/reactivity/Atom";
4
4
  import { draft } from "./draft.js";
@@ -6,7 +6,7 @@ import { literalChoices, messageAt, messagesByField, schemaFeedback } from "./me
6
6
  import { pathMessageAt } from "./paths.js";
7
7
  import { persistence } from "./persistence.js";
8
8
  import { fromRef, propertyRef } from "./refs.js";
9
- import { checkOf, choicesOf, FieldFailure, fieldOf, holder, Invalid, } from "./shape.js";
9
+ import { FieldFailure, Invalid } from "./shape.js";
10
10
  import { statusOf } from "./statusOf.js";
11
11
  import { trackRejections } from "./trackRejections.js";
12
12
  export function form(schema, config) {
@@ -17,24 +17,17 @@ export function form(schema, config) {
17
17
  const editing = draft(initialValues, config.persistedDraft ? persistence(schema, config.persistedDraft) : undefined);
18
18
  const { values } = editing;
19
19
  const status = statusOf();
20
- const noted = trackRejections(holder(values), config.arrayKeys, status);
21
- const held = new Map();
20
+ const noted = trackRejections(values, config.arrayKeys, status);
21
+ const held = {};
22
22
  function refFor(name) {
23
- const known = held.get(name);
23
+ const known = Object.hasOwn(held, name) ? held[name] : undefined;
24
24
  if (known !== undefined) {
25
25
  return known;
26
26
  }
27
- const made = propertyRef(holder(values), name);
28
- held.set(name, made);
27
+ const made = propertyRef(values, name);
28
+ held[name] = made;
29
29
  return made;
30
30
  }
31
- const offered = new Map();
32
- for (const [name, member] of Object.entries(schema.fields)) {
33
- const choices = literalChoices(member.ast);
34
- if (choices !== undefined) {
35
- offered.set(name, choices);
36
- }
37
- }
38
31
  const valuesAtom = fromRef(values);
39
32
  const decoded = runtime.atom((get) => decode(get(valuesAtom)).pipe(Effect.match({
40
33
  onFailure: (issue) => Result.fail(issue),
@@ -50,7 +43,7 @@ export function form(schema, config) {
50
43
  const settled = Atom.debounce(current, debounce);
51
44
  const answered = runtime.atom((get) => {
52
45
  const input = get(settled);
53
- return Effect.map(checkOf(check)(input), (message) => ({
46
+ return Effect.map(check(input), (message) => ({
54
47
  input,
55
48
  message,
56
49
  }));
@@ -83,14 +76,18 @@ export function form(schema, config) {
83
76
  refFor(name).set(value);
84
77
  status.touch(name);
85
78
  },
86
- choices: (name) => choicesOf(offered.get(name)),
79
+ choices: (name) => {
80
+ const member = schema.fields[name];
81
+ const decodeChoice = SchemaParser.decodeUnknownSync(Schema.toEncoded(schema), { disableChecks: true });
82
+ return (member ? literalChoices(member.ast) : undefined)?.map((value) => decodeChoice({ ...initialValues, [name]: value })[name]);
83
+ },
87
84
  dirty: editing.dirty,
88
85
  error,
89
86
  errorAt: Atom.family((path) => {
90
87
  const message = schemaErrors.at(path);
91
88
  return Atom.readable((get) => get(status.touched)[path[0]] === true || get(status.submitted) ? (pathMessageAt(get(status.paths), path) ?? get(message)) : undefined);
92
89
  }),
93
- field: (name) => fieldOf(refFor(name)),
90
+ field: refFor,
94
91
  receive: editing.receive,
95
92
  revert: editing.revert,
96
93
  submit,
package/dist/form.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"form.js","sourceRoot":"","sources":["../src/form.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"form.js","sourceRoot":"","sources":["../src/form.ts"],"names":[],"mappings":"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"}
package/dist/paths.d.ts CHANGED
@@ -1,13 +1,11 @@
1
1
  import type { Path } from "./shape.ts";
2
- type Key = (element: unknown) => PropertyKey;
2
+ export type Key = (element: unknown) => PropertyKey;
3
3
  export type KeySelectors = ReadonlyMap<string, Key>;
4
4
  export interface PathMessage {
5
5
  readonly message: string;
6
6
  readonly path: Path;
7
7
  }
8
- export declare function keySelector(selector: unknown): Key;
9
8
  export declare function asPath(path: string | Path): Path;
10
9
  export declare function retainedPath(path: Path, previous: unknown, current: unknown, keys: KeySelectors): Path | undefined;
11
10
  export declare function pathMessageAt(messages: readonly PathMessage[], path: readonly PropertyKey[]): string | undefined;
12
- export {};
13
11
  //# sourceMappingURL=paths.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"paths.d.ts","sourceRoot":"","sources":["../src/paths.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AAEvC,KAAK,GAAG,GAAG,CAAC,OAAO,EAAE,OAAO,KAAK,WAAW,CAAC;AAC7C,MAAM,MAAM,YAAY,GAAG,WAAW,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;AAEpD,MAAM,WAAW,WAAW;IAC3B,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC;CACpB;AAED,wBAAgB,WAAW,CAAC,QAAQ,EAAE,OAAO,GAAG,GAAG,CAAC;AAKpD,wBAAgB,MAAM,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,CAEhD;AAqBD,wBAAgB,YAAY,CAAC,IAAI,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,YAAY,GAAG,IAAI,GAAG,SAAS,CAmBlH;AAED,wBAAgB,aAAa,CAAC,QAAQ,EAAE,SAAS,WAAW,EAAE,EAAE,IAAI,EAAE,SAAS,WAAW,EAAE,GAAG,MAAM,GAAG,SAAS,CAEhH"}
1
+ {"version":3,"file":"paths.d.ts","sourceRoot":"","sources":["../src/paths.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AAEvC,MAAM,MAAM,GAAG,GAAG,CAAC,OAAO,EAAE,OAAO,KAAK,WAAW,CAAC;AACpD,MAAM,MAAM,YAAY,GAAG,WAAW,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;AAEpD,MAAM,WAAW,WAAW;IAC3B,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC;CACpB;AAED,wBAAgB,MAAM,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI,CAEhD;AAqBD,wBAAgB,YAAY,CAAC,IAAI,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,YAAY,GAAG,IAAI,GAAG,SAAS,CAmBlH;AAED,wBAAgB,aAAa,CAAC,QAAQ,EAAE,SAAS,WAAW,EAAE,EAAE,IAAI,EAAE,SAAS,WAAW,EAAE,GAAG,MAAM,GAAG,SAAS,CAEhH"}
package/dist/paths.js CHANGED
@@ -1,7 +1,4 @@
1
1
  import { Equal } from "effect";
2
- export function keySelector(selector) {
3
- return selector;
4
- }
5
2
  export function asPath(path) {
6
3
  return typeof path === "string" ? [path] : path;
7
4
  }
package/dist/paths.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"paths.js","sourceRoot":"","sources":["../src/paths.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"paths.js","sourceRoot":"","sources":["../src/paths.ts"],"names":[],"mappings":"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"}
@@ -9,6 +9,7 @@ export interface PersistedDraftConfig {
9
9
  readonly key: string;
10
10
  readonly maxAgeMs?: number;
11
11
  readonly maxBytes?: number;
12
+ readonly now: () => number;
12
13
  readonly session?: DraftSession | undefined;
13
14
  readonly storage: () => DraftStorage;
14
15
  }
@@ -1 +1 @@
1
- {"version":3,"file":"persistence.d.ts","sourceRoot":"","sources":["../src/persistence.ts"],"names":[],"mappings":"AAAA,OAAO,EAAiB,MAAM,EAAgB,MAAM,QAAQ,CAAC;AAC7D,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAEtD,MAAM,WAAW,YAAY;IAC5B,QAAQ,CAAC,OAAO,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,MAAM,GAAG,IAAI,CAAC;IACjD,QAAQ,CAAC,UAAU,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAC;IAC3C,QAAQ,CAAC,OAAO,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;CACvD;AAED,MAAM,WAAW,oBAAoB;IACpC,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,OAAO,CAAC,EAAE,YAAY,GAAG,SAAS,CAAC;IAC5C,QAAQ,CAAC,OAAO,EAAE,MAAM,YAAY,CAAC;CACrC;AAED,MAAM,WAAW,WAAW,CAAC,OAAO;IACnC,QAAQ,CAAC,KAAK,EAAE,MAAM,IAAI,CAAC;IAC3B,QAAQ,CAAC,IAAI,EAAE,MAAM;QAAE,QAAQ,CAAC,QAAQ,EAAE,OAAO,CAAC;QAAC,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC;QAAC,QAAQ,CAAC,MAAM,EAAE,OAAO,CAAA;KAAE,GAAG,SAAS,CAAC;IAC9H,QAAQ,CAAC,KAAK,EAAE,CAAC,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,SAAS,MAAM,EAAE,KAAK,IAAI,CAAC;CACxF;AAED,wBAAgB,WAAW,CAAC,OAAO,SAAS,MAAM,CAAC,UAAU,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,oBAAoB,GAAG,WAAW,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC,CAmF7I"}
1
+ {"version":3,"file":"persistence.d.ts","sourceRoot":"","sources":["../src/persistence.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAgB,MAAM,QAAQ,CAAC;AAC9C,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAEtD,MAAM,WAAW,YAAY;IAC5B,QAAQ,CAAC,OAAO,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,MAAM,GAAG,IAAI,CAAC;IACjD,QAAQ,CAAC,UAAU,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAC;IAC3C,QAAQ,CAAC,OAAO,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;CACvD;AAED,MAAM,WAAW,oBAAoB;IACpC,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,GAAG,EAAE,MAAM,MAAM,CAAC;IAC3B,QAAQ,CAAC,OAAO,CAAC,EAAE,YAAY,GAAG,SAAS,CAAC;IAC5C,QAAQ,CAAC,OAAO,EAAE,MAAM,YAAY,CAAC;CACrC;AAED,MAAM,WAAW,WAAW,CAAC,OAAO;IACnC,QAAQ,CAAC,KAAK,EAAE,MAAM,IAAI,CAAC;IAC3B,QAAQ,CAAC,IAAI,EAAE,MAAM;QAAE,QAAQ,CAAC,QAAQ,EAAE,OAAO,CAAC;QAAC,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC;QAAC,QAAQ,CAAC,MAAM,EAAE,OAAO,CAAA;KAAE,GAAG,SAAS,CAAC;IAC9H,QAAQ,CAAC,KAAK,EAAE,CAAC,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,SAAS,MAAM,EAAE,KAAK,IAAI,CAAC;CACxF;AAED,wBAAgB,WAAW,CAAC,OAAO,SAAS,MAAM,CAAC,UAAU,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,oBAAoB,GAAG,WAAW,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC,CAmF7I"}
@@ -1,4 +1,4 @@
1
- import { Clock, Effect, Schema, SchemaParser } from "effect";
1
+ import { Schema, SchemaParser } from "effect";
2
2
  export function persistence(schema, config) {
3
3
  const encoded = Schema.toEncoded(schema);
4
4
  const StoredDraft = Schema.Struct({
@@ -49,7 +49,7 @@ export function persistence(schema, config) {
49
49
  return undefined;
50
50
  }
51
51
  const value = bytes(raw) <= maxBytes ? JSON.parse(raw) : undefined;
52
- const now = Effect.runSync(Clock.currentTimeMillis);
52
+ const now = config.now();
53
53
  if (valid(value)
54
54
  && value.session === session
55
55
  && Number.isFinite(maxAgeMs)
@@ -68,7 +68,7 @@ export function persistence(schema, config) {
68
68
  return;
69
69
  }
70
70
  attempt(() => {
71
- const raw = JSON.stringify({ baseline, edited, session, updatedAt: Effect.runSync(Clock.currentTimeMillis), values, version: 1 });
71
+ const raw = JSON.stringify({ baseline, edited, session, updatedAt: config.now(), values, version: 1 });
72
72
  const parsed = JSON.parse(raw);
73
73
  if (!(maxAgeMs > 0 && Number.isFinite(maxAgeMs) && Number.isFinite(maxBytes) && bytes(raw) <= maxBytes && valid(parsed))) {
74
74
  clear();
@@ -1 +1 @@
1
- {"version":3,"file":"persistence.js","sourceRoot":"","sources":["../src/persistence.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,QAAQ,CAAC;AAuB7D,MAAM,UAAU,WAAW,CAAoC,MAAe,EAAE,MAA4B;IAC3G,MAAM,OAAO,GAAG,MAAM,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC;IACzC,MAAM,WAAW,GAAG,MAAM,CAAC,MAAM,CAAC;QACjC,QAAQ,EAAE,MAAM,CAAC,OAAO;QACxB,MAAM,EAAE,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,MAAM,CAAC;QACnC,OAAO,EAAE,MAAM,CAAC,MAAM;QACtB,SAAS,EAAE,MAAM,CAAC,MAAM;QACxB,MAAM,EAAE,MAAM,CAAC,OAAO;QACtB,OAAO,EAAE,MAAM,CAAC,OAAO,CAAC,CAAC,CAAC;KAC1B,CAAC,CAAC;IACH,MAAM,KAAK,GAAG,MAAM,CAAC,EAAE,CAAC,WAAW,CAAC,CAAC;IACrC,MAAM,MAAM,GAAG,YAAY,CAAC,iBAAiB,CAAC,OAAO,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;IAChF,MAAM,QAAQ,GAAG,MAAM,CAAC,QAAQ,IAAI,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC;IAC5D,MAAM,QAAQ,GAAG,MAAM,CAAC,QAAQ,IAAI,GAAG,GAAG,IAAI,CAAC;IAC/C,SAAS,KAAK,CAAC,KAAa;QAC3B,OAAO,IAAI,WAAW,EAAE,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,UAAU,CAAC;IACnD,CAAC;IACD,MAAM,OAAO,GAAG,MAAM,CAAC,OAAO,CAAC;IAC/B,MAAM,OAAO,GAAG,MAAM,CAAC,OAAO,EAAE,EAAE,IAAI,EAAE,CAAC;IACzC,SAAS,MAAM;QACd,OAAO,MAAM,CAAC,OAAO,EAAE,MAAM,KAAK,KAAK,CAAC;IACzC,CAAC;IACD,SAAS,OAAO,CAAI,GAAY,EAAE,MAAmB;QACpD,IAAI,CAAC;YACJ,OAAO,GAAG,EAAE,CAAC;QACd,CAAC;QAAC,MAAM,CAAC;YACR,MAAM,EAAE,EAAE,CAAC;YACX,OAAO,SAAS,CAAC;QAClB,CAAC;IACF,CAAC;IACD,SAAS,KAAK;QACb,OAAO,CAAC,GAAG,EAAE,CAAC,OAAO,EAAE,CAAC,UAAU,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC;IACjD,CAAC;IACD,MAAM,CAAC,OAAO,EAAE,KAAK,CAAC,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,CAAC;IACzC,OAAO;QACN,KAAK,EAAE,GAAG,EAAE;YACX,IAAI,MAAM,EAAE,EAAE,CAAC;gBACd,KAAK,EAAE,CAAC;YACT,CAAC;QACF,CAAC;QACD,IAAI,EAAE,GAAG,EAAE,CACV,OAAO,CAAC,GAAG,EAAE;YACZ,IAAI,CAAC,MAAM,EAAE,EAAE,CAAC;gBACf,OAAO,SAAS,CAAC;YAClB,CAAC;YACD,MAAM,GAAG,GAAG,OAAO,EAAE,CAAC,OAAO,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;YAC1C,IAAI,GAAG,KAAK,IAAI,EAAE,CAAC;gBAClB,OAAO,SAAS,CAAC;YAClB,CAAC;YACD,MAAM,KAAK,GAAY,KAAK,CAAC,GAAG,CAAC,IAAI,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;YAC5E,MAAM,GAAG,GAAG,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,iBAAiB,CAAC,CAAC;YACpD,IACC,KAAK,CAAC,KAAK,CAAC;mBACT,KAAK,CAAC,OAAO,KAAK,OAAO;mBACzB,MAAM,CAAC,QAAQ,CAAC,QAAQ,CAAC;mBACzB,MAAM,CAAC,QAAQ,CAAC,QAAQ,CAAC;mBACzB,QAAQ,GAAG,CAAC;mBACZ,QAAQ,GAAG,CAAC;mBACZ,GAAG,GAAG,KAAK,CAAC,SAAS,IAAI,QAAQ;mBACjC,KAAK,CAAC,SAAS,IAAI,GAAG,EACxB,CAAC;gBACF,OAAO,EAAE,QAAQ,EAAE,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,EAAE,MAAM,EAAE,KAAK,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,EAAE,CAAC;YACjG,CAAC;YACD,KAAK,EAAE,CAAC;YACR,OAAO,SAAS,CAAC;QAClB,CAAC,EAAE,KAAK,CAAC;QACV,KAAK,EAAE,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,EAAE,EAAE;YACnC,IAAI,CAAC,MAAM,EAAE,EAAE,CAAC;gBACf,OAAO;YACR,CAAC;YACD,OAAO,CAAC,GAAG,EAAE;gBACZ,MAAM,GAAG,GAAG,IAAI,CAAC,SAAS,CAAC,EAAE,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,SAAS,EAAE,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,iBAAiB,CAAC,EAAE,MAAM,EAAE,OAAO,EAAE,CAAC,EAAE,CAAC,CAAC;gBAClI,MAAM,MAAM,GAAY,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;gBACxC,IAAI,CAAC,CAAC,QAAQ,GAAG,CAAC,IAAI,MAAM,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,MAAM,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,KAAK,CAAC,GAAG,CAAC,IAAI,QAAQ,IAAI,KAAK,CAAC,MAAM,CAAC,CAAC,EAAE,CAAC;oBAC1H,KAAK,EAAE,CAAC;oBACR,OAAO;gBACR,CAAC;gBACD,MAAM,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;gBACxB,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;gBACtB,OAAO,EAAE,CAAC,OAAO,CAAC,MAAM,CAAC,GAAG,EAAE,GAAG,CAAC,CAAC;YACpC,CAAC,EAAE,KAAK,CAAC,CAAC;QACX,CAAC;KACD,CAAC;AACH,CAAC"}
1
+ {"version":3,"file":"persistence.js","sourceRoot":"","sources":["../src/persistence.ts"],"names":[],"mappings":"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"}
package/dist/shape.d.ts CHANGED
@@ -59,10 +59,6 @@ export interface Form<TFields extends Fields, A, E, TRuntimeError> {
59
59
  readonly submitting: Atom.Atom<boolean>;
60
60
  readonly values: AtomRef.AtomRef<Encoded<TFields>>;
61
61
  }
62
- export type Holder = AtomRef.AtomRef<Readonly<Record<string, unknown>>>;
63
- export declare function holder(values: object): Holder;
64
- export declare function fieldOf<TValue>(ref: AtomRef.AtomRef<unknown>): AtomRef.AtomRef<TValue>;
65
- export declare function choicesOf<TValue>(choices: readonly unknown[] | undefined): readonly TValue[] | undefined;
66
- export declare function checkOf<R>(check: unknown): (value: unknown) => Effect.Effect<string | undefined, never, R>;
62
+ export type Holder = AtomRef.ReadonlyRef<Readonly<Record<string, unknown>>>;
67
63
  export {};
68
64
  //# sourceMappingURL=shape.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"shape.d.ts","sourceRoot":"","sources":["../src/shape.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"shape.d.ts","sourceRoot":"","sources":["../src/shape.ts"],"names":[],"mappings":"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"}
package/dist/shape.js CHANGED
@@ -3,16 +3,4 @@ export class FieldFailure extends Data.TaggedError("FieldFailure") {
3
3
  }
4
4
  export class Invalid extends Data.TaggedError("Invalid") {
5
5
  }
6
- export function holder(values) {
7
- return values;
8
- }
9
- export function fieldOf(ref) {
10
- return ref;
11
- }
12
- export function choicesOf(choices) {
13
- return choices;
14
- }
15
- export function checkOf(check) {
16
- return check;
17
- }
18
6
  //# sourceMappingURL=shape.js.map
package/dist/shape.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"shape.js","sourceRoot":"","sources":["../src/shape.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAuD,MAAM,QAAQ,CAAC;AA0BnF,MAAM,OAAO,YAAa,SAAQ,IAAI,CAAC,WAAW,CAAC,cAAc,CAI/D;CAAG;AAEL,MAAM,OAAO,OAAQ,SAAQ,IAAI,CAAC,WAAW,CAAC,SAAS,CAErD;CAAG;AA0CL,MAAM,UAAU,MAAM,CAAC,MAAc;IACpC,OAAO,MAAM,CAAC;AACf,CAAC;AAGD,MAAM,UAAU,OAAO,CAAC,GAA6B;IACpD,OAAO,GAAG,CAAC;AACZ,CAAC;AAGD,MAAM,UAAU,SAAS,CAAC,OAAuC;IAChE,OAAO,OAAO,CAAC;AAChB,CAAC;AAGD,MAAM,UAAU,OAAO,CAAC,KAAc;IACrC,OAAO,KAAK,CAAC;AACd,CAAC"}
1
+ {"version":3,"file":"shape.js","sourceRoot":"","sources":["../src/shape.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAuD,MAAM,QAAQ,CAAC;AA0BnF,MAAM,OAAO,YAAa,SAAQ,IAAI,CAAC,WAAW,CAAC,cAAc,CAI/D;CAAG;AAEL,MAAM,OAAO,OAAQ,SAAQ,IAAI,CAAC,WAAW,CAAC,SAAS,CAErD;CAAG"}
@@ -1,5 +1,5 @@
1
1
  import { Effect } from "effect";
2
- import { type Holder } from "./shape.ts";
2
+ import { type ArrayKeys, type Fields, type Holder } from "./shape.ts";
3
3
  import type { statusOf } from "./statusOf.ts";
4
- export declare function trackRejections(values: Holder, selectors: Readonly<Record<string, unknown>> | undefined, status: ReturnType<typeof statusOf>): (submitted: unknown) => (cause: unknown) => Effect.Effect<void>;
4
+ export declare function trackRejections<TFields extends Fields>(values: Holder, selectors: ArrayKeys<TFields> | undefined, status: ReturnType<typeof statusOf>): (submitted: unknown) => (cause: unknown) => Effect.Effect<void>;
5
5
  //# sourceMappingURL=trackRejections.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"trackRejections.d.ts","sourceRoot":"","sources":["../src/trackRejections.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAEhC,OAAO,EAAgB,KAAK,MAAM,EAAE,MAAM,YAAY,CAAC;AACvD,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAE9C,wBAAgB,eAAe,CAAC,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,GAAG,SAAS,EAAE,MAAM,EAAE,UAAU,CAAC,OAAO,QAAQ,CAAC,eAOzH,OAAO,aACjB,OAAO,KAAG,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAStC"}
1
+ {"version":3,"file":"trackRejections.d.ts","sourceRoot":"","sources":["../src/trackRejections.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAEhC,OAAO,EAAE,KAAK,SAAS,EAAgB,KAAK,MAAM,EAAE,KAAK,MAAM,EAAE,MAAM,YAAY,CAAC;AACpF,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAE9C,wBAAgB,eAAe,CAAC,OAAO,SAAS,MAAM,EACrD,MAAM,EAAE,MAAM,EACd,SAAS,EAAE,SAAS,CAAC,OAAO,CAAC,GAAG,SAAS,EACzC,MAAM,EAAE,UAAU,CAAC,OAAO,QAAQ,CAAC,eAQhB,OAAO,aACjB,OAAO,KAAG,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAStC"}
@@ -1,8 +1,8 @@
1
1
  import { Effect } from "effect";
2
- import { asPath, keySelector, retainedPath } from "./paths.js";
2
+ import { asPath, retainedPath } from "./paths.js";
3
3
  import { FieldFailure } from "./shape.js";
4
4
  export function trackRejections(values, selectors, status) {
5
- const keys = new Map(Object.entries(selectors ?? {}).map(([name, select]) => [name, keySelector(select)]));
5
+ const keys = new Map(Object.entries(selectors ?? {}));
6
6
  let previous = values.value;
7
7
  values.subscribe((next) => {
8
8
  status.rebase(previous, next, keys);
@@ -1 +1 @@
1
- {"version":3,"file":"trackRejections.js","sourceRoot":"","sources":["../src/trackRejections.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAChC,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAC/D,OAAO,EAAE,YAAY,EAAe,MAAM,YAAY,CAAC;AAGvD,MAAM,UAAU,eAAe,CAAC,MAAc,EAAE,SAAwD,EAAE,MAAmC;IAC5I,MAAM,IAAI,GAAG,IAAI,GAAG,CAAC,MAAM,CAAC,OAAO,CAAC,SAAS,IAAI,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,IAAI,EAAE,MAAM,CAAC,EAAE,EAAE,CAAC,CAAC,IAAI,EAAE,WAAW,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC;IAC3G,IAAI,QAAQ,GAAG,MAAM,CAAC,KAAK,CAAC;IAC5B,MAAM,CAAC,SAAS,CAAC,CAAC,IAAI,EAAE,EAAE;QACzB,MAAM,CAAC,MAAM,CAAC,QAAQ,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC;QACpC,QAAQ,GAAG,IAAI,CAAC;IACjB,CAAC,CAAC,CAAC;IACH,OAAO,CAAC,SAAkB,EAAE,EAAE,CAC7B,CAAC,KAAc,EAAuB,EAAE,CACvC,MAAM,CAAC,IAAI,CAAC,GAAG,EAAE;QAChB,IAAI,KAAK,YAAY,YAAY,EAAE,CAAC;YACnC,MAAM,IAAI,GAAG,YAAY,CAAC,KAAK,CAAC,QAAQ,IAAI,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,SAAS,EAAE,MAAM,CAAC,KAAK,EAAE,IAAI,CAAC,CAAC;YAC/F,IAAI,IAAI,KAAK,SAAS,EAAE,CAAC;gBACxB,MAAM,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC,OAAO,CAAC,CAAC;YAClC,CAAC;QACF,CAAC;IACF,CAAC,CAAC,CAAC;AACN,CAAC"}
1
+ {"version":3,"file":"trackRejections.js","sourceRoot":"","sources":["../src/trackRejections.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAChC,OAAO,EAAE,MAAM,EAAY,YAAY,EAAE,MAAM,YAAY,CAAC;AAC5D,OAAO,EAAkB,YAAY,EAA4B,MAAM,YAAY,CAAC;AAGpF,MAAM,UAAU,eAAe,CAC9B,MAAc,EACd,SAAyC,EACzC,MAAmC;IAEnC,MAAM,IAAI,GAA6B,IAAI,GAAG,CAAC,MAAM,CAAC,OAAO,CAAC,SAAS,IAAI,EAAE,CAAC,CAAC,CAAC;IAChF,IAAI,QAAQ,GAAG,MAAM,CAAC,KAAK,CAAC;IAC5B,MAAM,CAAC,SAAS,CAAC,CAAC,IAAI,EAAE,EAAE;QACzB,MAAM,CAAC,MAAM,CAAC,QAAQ,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC;QACpC,QAAQ,GAAG,IAAI,CAAC;IACjB,CAAC,CAAC,CAAC;IACH,OAAO,CAAC,SAAkB,EAAE,EAAE,CAC7B,CAAC,KAAc,EAAuB,EAAE,CACvC,MAAM,CAAC,IAAI,CAAC,GAAG,EAAE;QAChB,IAAI,KAAK,YAAY,YAAY,EAAE,CAAC;YACnC,MAAM,IAAI,GAAG,YAAY,CAAC,KAAK,CAAC,QAAQ,IAAI,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,SAAS,EAAE,MAAM,CAAC,KAAK,EAAE,IAAI,CAAC,CAAC;YAC/F,IAAI,IAAI,KAAK,SAAS,EAAE,CAAC;gBACxB,MAAM,CAAC,IAAI,CAAC,IAAI,EAAE,KAAK,CAAC,OAAO,CAAC,CAAC;YAClC,CAAC;QACF,CAAC;IACF,CAAC,CAAC,CAAC;AACN,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@shivaedev/form",
3
- "version": "0.7.0",
3
+ "version": "0.8.0",
4
4
  "description": "Schema-derived Effect atom forms with optional React hooks",
5
5
  "keywords": [
6
6
  "effect"
@@ -43,21 +43,21 @@
43
43
  "README.md"
44
44
  ],
45
45
  "devDependencies": {
46
- "@effect/atom-react": "4.0.5",
47
- "@effect/vitest": "4.0.5",
48
- "@shivaedev/quality": "0.42.0",
49
- "@shivaedev/test": "0.10.0",
50
- "@shivaedev/test-story": "0.21.0",
46
+ "@effect/atom-react": "4.0.6",
47
+ "@effect/vitest": "4.0.6",
48
+ "@shivaedev/quality": "0.46.0",
49
+ "@shivaedev/test": "0.11.0",
50
+ "@shivaedev/test-story": "0.25.0",
51
51
  "@types/node": "24.19.2",
52
52
  "@types/react": "19.3.0",
53
- "effect": "4.0.5",
53
+ "effect": "4.0.6",
54
54
  "react": "19.3.1",
55
55
  "typescript": "7.0.2",
56
56
  "vitest": "5.0.5"
57
57
  },
58
58
  "peerDependencies": {
59
- "@effect/atom-react": "4.0.5",
60
- "effect": "4.0.5",
59
+ "@effect/atom-react": "4.0.6",
60
+ "effect": "4.0.6",
61
61
  "react": "19.3.1"
62
62
  },
63
63
  "peerDependenciesMeta": {
package/src/form.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { Effect, Equal, Result, type Schema, type SchemaIssue, SchemaParser } from "effect";
1
+ import { Effect, Equal, Result, Schema, type SchemaIssue, SchemaParser } from "effect";
2
2
  import * as AsyncResult from "effect/reactivity/AsyncResult";
3
3
  import * as Atom from "effect/reactivity/Atom";
4
4
  import type * as AtomRef from "effect/reactivity/AtomRef";
@@ -7,21 +7,7 @@ import { literalChoices, messageAt, messagesByField, schemaFeedback } from "./me
7
7
  import { pathMessageAt } from "./paths.ts";
8
8
  import { persistence } from "./persistence.ts";
9
9
  import { fromRef, propertyRef } from "./refs.ts";
10
- import {
11
- type Config,
12
- checkOf,
13
- choicesOf,
14
- type Decoded,
15
- type Encoded,
16
- FieldFailure,
17
- type Fields,
18
- type Form,
19
- fieldOf,
20
- holder,
21
- Invalid,
22
- type Name,
23
- type Submitter,
24
- } from "./shape.ts";
10
+ import { type Config, type Decoded, type Encoded, FieldFailure, type Fields, type Form, Invalid, type Name, type Submitter } from "./shape.ts";
25
11
  import { statusOf } from "./statusOf.ts";
26
12
  import { trackRejections } from "./trackRejections.ts";
27
13
 
@@ -31,32 +17,26 @@ export function form<TFields extends Fields, TValue, TError, TServices, TRuntime
31
17
  ): Form<TFields, TValue, TError, TRuntimeError> {
32
18
  const { initialValues, onSubmit, runtime } = config;
33
19
  const debounce = config.debounce ?? "300 millis";
34
- const checks: ReadonlyMap<string, unknown> = new Map(Object.entries(config.checks ?? {}));
20
+ const checks: ReadonlyMap<string, (value: Encoded<TFields>[Name<TFields>]) => Effect.Effect<string | undefined, never, TServices>> = new Map(
21
+ Object.entries(config.checks ?? {}),
22
+ );
35
23
  const decode = SchemaParser.decodeUnknownEffect(schema, { errors: "all" });
36
24
 
37
25
  const editing = draft(initialValues, config.persistedDraft ? persistence(schema, config.persistedDraft) : undefined);
38
26
  const { values } = editing;
39
27
  const status = statusOf();
40
- const noted = trackRejections(holder(values), config.arrayKeys, status);
41
- const held = new Map<string, AtomRef.AtomRef<unknown>>();
42
- function refFor(name: string): AtomRef.AtomRef<unknown> {
43
- const known = held.get(name);
28
+ const noted = trackRejections(values, config.arrayKeys, status);
29
+ const held: { [TKey in Name<TFields>]?: AtomRef.AtomRef<Encoded<TFields>[TKey]> } = {};
30
+ function refFor<TKey extends Name<TFields>>(name: TKey): AtomRef.AtomRef<Encoded<TFields>[TKey]> {
31
+ const known = Object.hasOwn(held, name) ? held[name] : undefined;
44
32
  if (known !== undefined) {
45
33
  return known;
46
34
  }
47
- const made = propertyRef(holder(values), name);
48
- held.set(name, made);
35
+ const made = propertyRef(values, name);
36
+ held[name] = made;
49
37
  return made;
50
38
  }
51
39
 
52
- const offered = new Map<string, readonly unknown[]>();
53
- for (const [name, member] of Object.entries(schema.fields)) {
54
- const choices = literalChoices(member.ast);
55
- if (choices !== undefined) {
56
- offered.set(name, choices);
57
- }
58
- }
59
-
60
40
  const valuesAtom = fromRef(values);
61
41
 
62
42
  const decoded = runtime.atom((get) =>
@@ -70,7 +50,7 @@ export function form<TFields extends Fields, TValue, TError, TServices, TRuntime
70
50
 
71
51
  const schemaErrors = schemaFeedback(decoded);
72
52
 
73
- const checkError = Atom.family((name: string): Atom.Atom<string | undefined> => {
53
+ const checkError = Atom.family((name: Name<TFields>): Atom.Atom<string | undefined> => {
74
54
  const check = checks.get(name);
75
55
  if (check === undefined) {
76
56
  return Atom.make((): string | undefined => undefined);
@@ -79,7 +59,7 @@ export function form<TFields extends Fields, TValue, TError, TServices, TRuntime
79
59
  const settled = Atom.debounce(current, debounce);
80
60
  const answered = runtime.atom((get) => {
81
61
  const input = get(settled);
82
- return Effect.map(checkOf<TServices>(check)(input), (message) => ({
62
+ return Effect.map(check(input), (message) => ({
83
63
  input,
84
64
  message,
85
65
  }));
@@ -91,7 +71,7 @@ export function form<TFields extends Fields, TValue, TError, TServices, TRuntime
91
71
  });
92
72
  });
93
73
 
94
- const error = Atom.family((name: string) =>
74
+ const error = Atom.family((name: Name<TFields>) =>
95
75
  Atom.readable((get): string | undefined => {
96
76
  if (get(status.touched)[name] !== true && !get(status.submitted)) {
97
77
  return undefined;
@@ -123,7 +103,11 @@ export function form<TFields extends Fields, TValue, TError, TServices, TRuntime
123
103
  refFor(name).set(value);
124
104
  status.touch(name);
125
105
  },
126
- choices: <TName extends Name<TFields>>(name: TName) => choicesOf<Encoded<TFields>[TName]>(offered.get(name)),
106
+ choices: <TName extends Name<TFields>>(name: TName) => {
107
+ const member = schema.fields[name];
108
+ const decodeChoice = SchemaParser.decodeUnknownSync(Schema.toEncoded(schema), { disableChecks: true });
109
+ return (member ? literalChoices(member.ast) : undefined)?.map((value) => decodeChoice({ ...initialValues, [name]: value })[name]);
110
+ },
127
111
  dirty: editing.dirty,
128
112
  error,
129
113
  errorAt: Atom.family((path: readonly [Name<TFields>, ...PropertyKey[]]) => {
@@ -132,7 +116,7 @@ export function form<TFields extends Fields, TValue, TError, TServices, TRuntime
132
116
  get(status.touched)[path[0]] === true || get(status.submitted) ? (pathMessageAt(get(status.paths), path) ?? get(message)) : undefined,
133
117
  );
134
118
  }),
135
- field: <TName extends Name<TFields>>(name: TName) => fieldOf<Encoded<TFields>[TName]>(refFor(name)),
119
+ field: refFor,
136
120
  receive: editing.receive,
137
121
  revert: editing.revert,
138
122
  submit,
package/src/paths.ts CHANGED
@@ -1,7 +1,7 @@
1
1
  import { Equal } from "effect";
2
2
  import type { Path } from "./shape.ts";
3
3
 
4
- type Key = (element: unknown) => PropertyKey;
4
+ export type Key = (element: unknown) => PropertyKey;
5
5
  export type KeySelectors = ReadonlyMap<string, Key>;
6
6
 
7
7
  export interface PathMessage {
@@ -9,11 +9,6 @@ export interface PathMessage {
9
9
  readonly path: Path;
10
10
  }
11
11
 
12
- export function keySelector(selector: unknown): Key;
13
- export function keySelector(selector: unknown): unknown {
14
- return selector;
15
- }
16
-
17
12
  export function asPath(path: string | Path): Path {
18
13
  return typeof path === "string" ? [path] : path;
19
14
  }
@@ -1,4 +1,4 @@
1
- import { Clock, Effect, Schema, SchemaParser } from "effect";
1
+ import { Schema, SchemaParser } from "effect";
2
2
  import type { DraftSession } from "./draftSession.ts";
3
3
 
4
4
  export interface DraftStorage {
@@ -11,6 +11,7 @@ export interface PersistedDraftConfig {
11
11
  readonly key: string;
12
12
  readonly maxAgeMs?: number;
13
13
  readonly maxBytes?: number;
14
+ readonly now: () => number;
14
15
  readonly session?: DraftSession | undefined;
15
16
  readonly storage: () => DraftStorage;
16
17
  }
@@ -71,7 +72,7 @@ export function persistence<TSchema extends Schema.Constraint>(schema: TSchema,
71
72
  return undefined;
72
73
  }
73
74
  const value: unknown = bytes(raw) <= maxBytes ? JSON.parse(raw) : undefined;
74
- const now = Effect.runSync(Clock.currentTimeMillis);
75
+ const now = config.now();
75
76
  if (
76
77
  valid(value)
77
78
  && value.session === session
@@ -92,7 +93,7 @@ export function persistence<TSchema extends Schema.Constraint>(schema: TSchema,
92
93
  return;
93
94
  }
94
95
  attempt(() => {
95
- const raw = JSON.stringify({ baseline, edited, session, updatedAt: Effect.runSync(Clock.currentTimeMillis), values, version: 1 });
96
+ const raw = JSON.stringify({ baseline, edited, session, updatedAt: config.now(), values, version: 1 });
96
97
  const parsed: unknown = JSON.parse(raw);
97
98
  if (!(maxAgeMs > 0 && Number.isFinite(maxAgeMs) && Number.isFinite(maxBytes) && bytes(raw) <= maxBytes && valid(parsed))) {
98
99
  clear();
package/src/shape.ts CHANGED
@@ -71,24 +71,4 @@ export interface Form<TFields extends Fields, A, E, TRuntimeError> {
71
71
  readonly values: AtomRef.AtomRef<Encoded<TFields>>;
72
72
  }
73
73
 
74
- export type Holder = AtomRef.AtomRef<Readonly<Record<string, unknown>>>;
75
-
76
- export function holder(values: object): Holder;
77
- export function holder(values: object): unknown {
78
- return values;
79
- }
80
-
81
- export function fieldOf<TValue>(ref: AtomRef.AtomRef<unknown>): AtomRef.AtomRef<TValue>;
82
- export function fieldOf(ref: AtomRef.AtomRef<unknown>): unknown {
83
- return ref;
84
- }
85
-
86
- export function choicesOf<TValue>(choices: readonly unknown[] | undefined): readonly TValue[] | undefined;
87
- export function choicesOf(choices: readonly unknown[] | undefined): unknown {
88
- return choices;
89
- }
90
-
91
- export function checkOf<R>(check: unknown): (value: unknown) => Effect.Effect<string | undefined, never, R>;
92
- export function checkOf(check: unknown): unknown {
93
- return check;
94
- }
74
+ export type Holder = AtomRef.ReadonlyRef<Readonly<Record<string, unknown>>>;
@@ -1,10 +1,14 @@
1
1
  import { Effect } from "effect";
2
- import { asPath, keySelector, retainedPath } from "./paths.ts";
3
- import { FieldFailure, type Holder } from "./shape.ts";
2
+ import { asPath, type Key, retainedPath } from "./paths.ts";
3
+ import { type ArrayKeys, FieldFailure, type Fields, type Holder } from "./shape.ts";
4
4
  import type { statusOf } from "./statusOf.ts";
5
5
 
6
- export function trackRejections(values: Holder, selectors: Readonly<Record<string, unknown>> | undefined, status: ReturnType<typeof statusOf>) {
7
- const keys = new Map(Object.entries(selectors ?? {}).map(([name, select]) => [name, keySelector(select)]));
6
+ export function trackRejections<TFields extends Fields>(
7
+ values: Holder,
8
+ selectors: ArrayKeys<TFields> | undefined,
9
+ status: ReturnType<typeof statusOf>,
10
+ ) {
11
+ const keys: ReadonlyMap<string, Key> = new Map(Object.entries(selectors ?? {}));
8
12
  let previous = values.value;
9
13
  values.subscribe((next) => {
10
14
  status.rebase(previous, next, keys);