march-hare 0.16.0 → 0.17.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 CHANGED
@@ -394,10 +394,11 @@ Components that mount after a broadcast has already been dispatched automaticall
394
394
 
395
395
  ## Resource handling
396
396
 
397
- For remote data, declare an `app.Resource` at module scope. The resulting handle has two call forms:
397
+ For remote data, declare an `app.Resource` at module scope. The resulting handle has three call forms:
398
398
 
399
399
  - `resource.user.get(params)` — synchronous cache read, returns `User | null`. Use it in model literals, JSX, or anywhere you need the cached value without triggering a fetch.
400
400
  - `resource.user(params)` &mdash; produces an `Invocation` you pass to `context.actions.resource(...)` for the fetch path (with auto-threaded abort controller and a live handle to the per-`<Boundary>` Env).
401
+ - `resource.user.action(partial?)` &mdash; broadcast channeled action fired automatically after every successful fetch. Always invoke (`resource.user.action()`) before passing to `actions.useAction` or `actions.stream`; supply a subset of params to narrow the filter (more keys = stricter), or pass nothing to receive every fetch. Errors do not broadcast.
401
402
 
402
403
  Every successful fetch caches the response in a module-level slot keyed by the fetcher and the stringified params, so different param-sets are independent. Keep all resources in `resources.ts` and pull the whole module in as a namespace (`import * as resource from "./resources"`):
403
404
 
@@ -461,6 +462,44 @@ export default function Profile(): React.ReactElement {
461
462
  }
462
463
  ```
463
464
 
465
+ Every successful fetch also publishes an auto-broadcast via `resource.x.action(partial?)`. Any component &mdash; even one that never called the fetcher &mdash; can react via `actions.useAction` or render the latest payload with `actions.stream`. Call `.action()` with no arguments to match every fetch on the resource, or supply a subset of params to narrow the filter:
466
+
467
+ ```tsx
468
+ // greeting/actions.ts
469
+ import { app } from "../app";
470
+ import * as resource from "../resources";
471
+
472
+ type Model = { greeting: string | null };
473
+
474
+ function useActions() {
475
+ const context = app.useContext<Model>();
476
+ const actions = context.useActions({ greeting: null });
477
+
478
+ actions.useAction(resource.user.action(), (context, user) => {
479
+ context.actions.produce(
480
+ ({ model }) => void (model.greeting = `Welcome, ${user.name}`),
481
+ );
482
+ });
483
+
484
+ return actions;
485
+ }
486
+
487
+ export default function Greeting() {
488
+ const [model] = useActions();
489
+ return <span>{model.greeting ?? "…"}</span>;
490
+ }
491
+ ```
492
+
493
+ Or render the most recent payload declaratively without a local model field:
494
+
495
+ ```tsx
496
+ {
497
+ actions.stream(resource.user.action(), (user) => <span>{user.name}</span>);
498
+ }
499
+ ```
500
+
501
+ The broadcast cache is sharded by `(action, channel)`, so a late-mounting subscriber replays every cached entry whose channel satisfies its filter &mdash; a `stream` panel that mounts after the page's data has already loaded still paints with the cached value rather than waiting for the next fetch.
502
+
464
503
  `context.actions.resource(invocation)` returns a chainable thenable:
465
504
 
466
505
  - `.exceeds({ minutes: 5 })` &mdash; short-circuits when the per-params cache age is within the freshness window. Accepts a `Temporal.Duration`, a `DurationLike` object, or an ISO 8601 duration string. `Temporal` is read from the host runtime &ndash; bring a polyfill (e.g. [`@js-temporal/polyfill`](https://github.com/js-temporal/temporal-polyfill)) if your target doesn't expose it natively.
@@ -556,7 +595,7 @@ export const app = App({
556
595
  get: (key) => localStorage.getItem(key),
557
596
  set: (key, value) => localStorage.setItem(key, value),
558
597
  remove: (key) => localStorage.removeItem(key),
559
- clear: () => localStorage.clear(),
598
+ keys: () => Object.keys(localStorage),
560
599
  }),
561
600
  });
562
601
  ```
@@ -621,15 +660,15 @@ export const app = App<AppEnv>({
621
660
  get: (key) => localStorage.getItem(key),
622
661
  set: (key, value) => localStorage.setItem(key, value),
623
662
  remove: (key) => localStorage.removeItem(key),
624
- clear: () => localStorage.clear(),
663
+ keys: () => Object.keys(localStorage),
625
664
  key: ({ env }) => env.session?.accessToken ?? "",
626
665
  }),
627
666
  });
628
667
  ```
629
668
 
630
- Successful writes for Alice land under `alice:0:{...}`; Bob's land under `bob:0:{...}`. Return `""`, `null`, or `undefined` to skip prefixing &ndash; useful for the signed-out gap, where the scope is genuinely empty.
669
+ Successful writes for Alice land under `mh:alice:0:{...}`; Bob's land under `mh:bob:0:{...}`. The Cache layer prepends a global `mh:` namespace so `cache.clear()` and partial-match eviction can scope themselves to March Hare's own entries on shared backends, leaving third-party `localStorage` state untouched. Return `""`, `null`, or `undefined` from `key(context)` to skip the per-context prefix &ndash; useful for the signed-out gap.
631
670
 
632
- The adapter contract is **strictly synchronous** &ndash; `get` / `set` / `remove` / `clear` all return immediately, with no `Promise`. The model-literal read (`{ user: resource.user.get() }`) is evaluated during render and has no place to wait. React Native projects should use [`react-native-mmkv`](https://github.com/mrousavy/react-native-mmkv), which is sync out of the box and drops straight into the contract; `AsyncStorage` is incompatible. Truly async backends (IndexedDB, `chrome.storage.local`) need a sync facade hydrated at app entry &ndash; see the [storage recipe](./recipes/storage.md).
671
+ The adapter contract is **strictly synchronous** &ndash; `get` / `set` / `remove` / `keys` all return immediately, with no `Promise`. The model-literal read (`{ user: resource.user.get() }`) is evaluated during render and has no place to wait. React Native projects should use [`react-native-mmkv`](https://github.com/mrousavy/react-native-mmkv), which is sync out of the box and drops straight into the contract; `AsyncStorage` is incompatible. Truly async backends (IndexedDB, `chrome.storage.local`) need a sync facade hydrated at app entry &ndash; see the [storage recipe](./recipes/storage.md).
633
672
 
634
673
  See the [storage recipe](./recipes/storage.md) for backend adapters (React Native `react-native-mmkv`, browser `localStorage`, browser extension `chrome.storage`), sign-out purge, and the `unset` sentinel that keeps "nothing stored" distinct from "a legitimately stored null".
635
674
 
@@ -670,6 +709,8 @@ actions.dispatch(Actions.UserUpdated, user);
670
709
 
671
710
  Channel values support non-nullable primitives: `string`, `number`, `boolean`, or `symbol`. By convention, use uppercase keys like `{UserId: 4}` to distinguish controller keys from payload properties.
672
711
 
712
+ Matching follows a single rule: every key the **subscriber** supplies must be present and equal on the dispatch channel. The subscriber's controller is the filter, more keys narrow it. Extra keys on the dispatch channel are ignored, so the dispatcher is free to be more specific than any single subscriber needs. Uncalled actions on either side bypass channel filtering entirely. See the [channeled-actions recipe](./recipes/channeled-actions.md#channel-matching) for the full matrix.
713
+
673
714
  ## Multicast actions
674
715
 
675
716
  For scoped communication between component groups, declare a multicast action class and open a scope via `app.Scope<typeof MulticastActions>()`. The generic carries the multicast surface at the type level &mdash; `scope.useContext().actions.dispatch` widens to include those actions on top of the local `Actions` class, the same way `Actions.Broadcast = BroadcastActions` widens for broadcasts. Render `<scope.Boundary>` once at the root of the subtree the scope governs:
@@ -16,19 +16,11 @@ export declare function withGetters<P extends Props>(a: P, b: RefObject<P>): P;
16
16
  * the generator function's name.
17
17
  */
18
18
  export declare function isGenerator(result: unknown): result is Generator | AsyncGenerator;
19
- /**
20
- * Sentinel passed as the dispatch channel during mount replay. Channeled
21
- * handlers check for this to skip replay &mdash; they require specific
22
- * channel context and cannot meaningfully process a replay without it.
23
- *
24
- * @internal
25
- */
26
- export declare const replay: unique symbol;
27
19
  /**
28
20
  * Invokes all listeners for an event and returns a promise that resolves
29
21
  * when every handler has settled. For {@link BroadcastEmitter} instances the
30
- * payload is cached before listeners fire so late-mounting components still
31
- * see the latest value.
22
+ * payload is cached &mdash; sharded by channel &mdash; before listeners
23
+ * fire so late-mounting components see every cached entry.
32
24
  *
33
25
  * @internal
34
26
  */
@@ -147,19 +139,29 @@ export declare function useDispatchers(): Dispatchers;
147
139
  */
148
140
  export declare function useRegisterHandler<M extends Model | void, A extends Actions | void, D extends Props>(scope: React.RefObject<Scope<M, A, D>>, action: ActionId | HandlerPayload | ChanneledAction, handler: (context: HandlerContext<M, A, D>, payload: unknown) => void | Promise<void> | AsyncGenerator | Generator): void;
149
141
  /**
150
- * Checks if a dispatch channel matches a registered handler channel.
151
- * All properties in the dispatch channel must match the corresponding properties in the registered channel.
142
+ * Checks whether a dispatch channel satisfies a registered handler's
143
+ * channel filter. The handler's channel is the filter: every key the
144
+ * subscriber supplied must be present and equal on the dispatch channel.
145
+ * Extra keys on the dispatch channel are ignored &mdash; the dispatcher
146
+ * is free to be more specific than any single subscriber needs.
147
+ *
148
+ * Mental model: "the subscriber declares everything it wants matched
149
+ * against; the dispatcher matches what it can." A subscriber that
150
+ * registers no channel keys (`{}` or no channel at all) matches every
151
+ * dispatch on the action.
152
152
  *
153
153
  * @param dispatchChannel - The channel from the dispatch call (from ChanneledAction)
154
154
  * @param registeredChannel - The channel registered with useAction
155
- * @returns `true` if all dispatch channel properties match the registered channel
155
+ * @returns `true` if every key on the registered channel is satisfied by the dispatch channel
156
156
  *
157
157
  * @example
158
158
  * ```ts
159
- * matchesChannel({ UserId: 1 }, { UserId: 1 }); // true
160
- * matchesChannel({ UserId: 1 }, { UserId: 2 }); // false
161
- * matchesChannel({ UserId: 1 }, { UserId: 1, Role: "admin" }); // true (subset match)
162
- * matchesChannel({ UserId: 1, Role: "admin" }, { UserId: 1 }); // false (missing Role)
159
+ * matchesChannel({ UserId: 1 }, { UserId: 1 }); // true (exact)
160
+ * matchesChannel({ UserId: 1, Role: "admin" }, { UserId: 1 }); // true (subscriber narrower)
161
+ * matchesChannel({ UserId: 1 }, { UserId: 1, Role: "admin" }); // false (subscriber asked for Role, dispatch did not supply it)
162
+ * matchesChannel({ UserId: 1 }, { UserId: 2 }); // false (value mismatch)
163
+ * matchesChannel({ UserId: 1, Role: "admin" }, {}); // true (subscriber filters nothing)
164
+ * matchesChannel({}, { UserId: 1 }); // false (subscriber asked for UserId, dispatch did not supply it)
163
165
  * ```
164
166
  */
165
167
  export declare function matchesChannel(dispatchChannel: Filter, registeredChannel: Filter): boolean;
@@ -50,7 +50,7 @@ export type { AppHandle } from './types.js';
50
50
  * get: (key) => localStorage.getItem(key),
51
51
  * set: (key, value) => localStorage.setItem(key, value),
52
52
  * remove: (key) => localStorage.removeItem(key),
53
- * clear: () => localStorage.clear(),
53
+ * keys: () => Object.keys(localStorage),
54
54
  * }),
55
55
  * });
56
56
  *
@@ -1,25 +1,51 @@
1
1
  import { default as EventEmitter } from 'eventemitter3';
2
+ import { Filter } from '../../../types/index.js';
2
3
  import * as React from "react";
3
4
  /**
4
- * EventEmitter subclass that caches the latest payload per event.
5
- *
6
- * When a broadcast or multicast action is dispatched, the payload is
7
- * stored so that late-mounting components can replay it via
8
- * {@link useLifecycles} and handlers can read it via
9
- * `context.actions.final()`.
5
+ * Cache entry stored per `(event, channelHash)`. The original channel
6
+ * object is preserved so mount replay can re-emit with the exact
7
+ * channel the producer used &mdash; otherwise late-mounting subscribers
8
+ * could not satisfy filtered-channel matching.
9
+ */
10
+ type Entry = {
11
+ readonly channel: Filter | undefined;
12
+ readonly value: unknown;
13
+ };
14
+ /**
15
+ * EventEmitter subclass that caches the latest payload per `(event,
16
+ * channel)` pair. When a broadcast or multicast action is dispatched,
17
+ * the payload is stored so that late-mounting components can replay it
18
+ * via {@link useLifecycles} and handlers can read it via
19
+ * `context.actions.final()`. Cache entries are keyed by both the
20
+ * action and the channel object &mdash; multi-channel actions retain
21
+ * one entry per channel rather than overwriting on every dispatch.
10
22
  */
11
23
  export declare class BroadcastEmitter extends EventEmitter {
12
24
  private cache;
25
+ private latest;
13
26
  emit(event: string | symbol, ...args: unknown[]): boolean;
14
27
  /**
15
- * Cache a value for a given event without emitting to listeners.
16
- * Used by {@link emitAsync} to preserve caching when bypassing `emit()`.
28
+ * Cache a value for a given event/channel pair without emitting to
29
+ * listeners. Used by {@link emitAsync} to preserve caching when
30
+ * bypassing `emit()`.
17
31
  */
18
- setCache(event: string | symbol, value: unknown): void;
32
+ setCache(event: string | symbol, value: unknown, channel: Filter | undefined): void;
19
33
  /**
20
- * Retrieve the last emitted payload for a given event.
34
+ * Retrieve the most recently cached payload across every channel for
35
+ * a given event. Returns `undefined` if no value has ever been
36
+ * dispatched. Use {@link getCachedAll} when channel-specific replay
37
+ * is required &mdash; this overload exists for `context.actions
38
+ * .final()`, which resolves to the most recent broadcast regardless
39
+ * of channel.
21
40
  */
22
41
  getCached(event: string | symbol): unknown;
42
+ /**
43
+ * Iterate every cached `(channel, value)` pair for a given event.
44
+ * Mount replay walks this to re-emit per-channel values so that
45
+ * late-mounting subscribers see the same broadcasts they would have
46
+ * received had they been mounted at dispatch time.
47
+ */
48
+ getCachedAll(event: string | symbol): Iterable<Entry>;
23
49
  /**
24
50
  * Emit without caching the payload. Used by the framework to publish
25
51
  * fire-and-forget events (such as `Lifecycle.Fault`) where late-mounting
@@ -37,3 +63,4 @@ export declare const Context: React.Context<BroadcastEmitter>;
37
63
  * @returns The BroadcastEmitter instance for distributed actions.
38
64
  */
39
65
  export declare function useBroadcast(): BroadcastEmitter;
66
+ export {};
@@ -13,23 +13,49 @@ export type CacheContext<E extends object> = {
13
13
  readonly env: E;
14
14
  };
15
15
  /**
16
- * Configuration accepted by the {@link Cache} factory. Combines the
17
- * synchronous {@link Adapter} (`get`/`set`/`remove`/`clear`/`keys?`)
18
- * with an optional `key(context)` callback in a single flat object,
19
- * so all the cache's plumbing lives in one literal at the call site.
20
- *
21
- * - `key` &mdash; derives a per-context cache scope. Called every time
22
- * a cache key is assembled with the same `{ env }` shape an
23
- * `app.Resource` fetcher receives; the returned string is prepended
24
- * to the per-resource namespace and params so different scopes
25
- * (e.g. one cache slot per access token, locale, or tenant id) can
26
- * coexist in the same backing store. Return `""`, `null`, or
27
- * `undefined` to skip prefixing &mdash; useful for "not signed in"
28
- * gaps where the scope is genuinely empty.
16
+ * Optional `key(context)` callback shared by both {@link CacheConfig}
17
+ * variants. Derives a per-context cache scope. Called every time a
18
+ * cache key is assembled with the same `{ env }` shape an
19
+ * `app.Resource` fetcher receives; the returned string is prepended
20
+ * to the per-resource namespace and params so different scopes
21
+ * (e.g. one cache slot per access token, locale, or tenant id) can
22
+ * coexist in the same backing store. Return `""`, `null`, or
23
+ * `undefined` to skip prefixing &mdash; useful for "not signed in"
24
+ * gaps where the scope is genuinely empty.
29
25
  */
30
- export type CacheConfig<E extends object> = Adapter & {
26
+ type CacheKeyOnly<E extends object> = {
31
27
  readonly key?: (context: CacheContext<E>) => string | null | undefined;
28
+ readonly get?: never;
29
+ readonly set?: never;
30
+ readonly remove?: never;
31
+ readonly keys?: never;
32
32
  };
33
+ type CacheAdapter<E extends object> = Adapter & {
34
+ readonly key?: (context: CacheContext<E>) => string | null | undefined;
35
+ };
36
+ /**
37
+ * Configuration accepted by the {@link Cache} factory. A discriminated
38
+ * union with two shapes:
39
+ *
40
+ * - **Adapter-only / adapter + `key`** &mdash; supply the four
41
+ * adapter methods (`get`/`set`/`remove`/`keys`) and an optional
42
+ * `key(context)` callback. The cache is backed by the adapter;
43
+ * persistence is the caller's responsibility. There is no `clear`
44
+ * &mdash; the Cache layer synthesises one by iterating `keys()`
45
+ * and removing only entries inside the `mh:` namespace it owns,
46
+ * so third-party state on shared backends stays untouched.
47
+ * - **`key`-only** &mdash; supply just `key(context)` (no adapter
48
+ * methods at all). The cache falls back to a per-instance in-memory
49
+ * adapter but still scopes every slot by the live Env, which is
50
+ * useful for tests, ephemeral state, or signed-out sessions where
51
+ * you want env-scoped isolation without touching storage.
52
+ *
53
+ * The split is enforced by the union: passing a partial adapter
54
+ * (e.g. just `get`) is a type error &mdash; either all four required
55
+ * adapter methods are present or none of them are. {@link Cache} also
56
+ * accepts no argument at all for a plain in-memory cache.
57
+ */
58
+ export type CacheConfig<E extends object> = CacheAdapter<E> | CacheKeyOnly<E>;
33
59
  /**
34
60
  * Persistence-aware cache for a single {@link Resource}. Wraps a
35
61
  * **strictly synchronous** {@link Adapter} (localStorage, MMKV,
@@ -55,11 +81,12 @@ export type CacheConfig<E extends object> = Adapter & {
55
81
  * persistent store; when supplied, the adapter is the **only** tier
56
82
  * &mdash; the Cache does not maintain a separate in-memory mirror.
57
83
  *
58
- * Pass `key(context)` alongside the adapter methods to scope cache
59
- * slots by the per-`<Boundary>` Env. The returned string is prepended
60
- * to every cache key the Resource layer assembles, so different
61
- * tenants / sessions / locales share the adapter without stepping on
62
- * each other.
84
+ * `key(context)` is independently optional. Pass it alongside the
85
+ * adapter methods to scope a persistent cache by the live Env, or on
86
+ * its own (with no adapter) for an env-scoped in-memory cache. The
87
+ * adapter methods are an all-or-nothing group: supply all four
88
+ * (`get`/`set`/`remove`/`keys`) or none. Supplying a partial adapter
89
+ * is a type error.
63
90
  *
64
91
  * The `E` generic lives on the {@link Cache} factory and on
65
92
  * {@link CacheConfig}: it parameterises the `key(context)` callback
@@ -80,7 +107,7 @@ export type CacheConfig<E extends object> = Adapter & {
80
107
  * get: (key) => localStorage.getItem(key),
81
108
  * set: (key, value) => localStorage.setItem(key, value),
82
109
  * remove: (key) => localStorage.removeItem(key),
83
- * clear: () => localStorage.clear(),
110
+ * keys: () => Object.keys(localStorage),
84
111
  * });
85
112
  *
86
113
  * // Multi-tenant: writes go under `${accessToken}:…`.
@@ -89,7 +116,12 @@ export type CacheConfig<E extends object> = Adapter & {
89
116
  * get: (key) => localStorage.getItem(key),
90
117
  * set: (key, value) => localStorage.setItem(key, value),
91
118
  * remove: (key) => localStorage.removeItem(key),
92
- * clear: () => localStorage.clear(),
119
+ * keys: () => Object.keys(localStorage),
120
+ * key: ({ env }) => env.session?.accessToken ?? "",
121
+ * });
122
+ *
123
+ * // Env-scoped in-memory cache: no adapter, just `key`.
124
+ * const cache = Cache<AppEnv>({
93
125
  * key: ({ env }) => env.session?.accessToken ?? "",
94
126
  * });
95
127
  *
@@ -160,11 +192,18 @@ export type Cache = {
160
192
  scope(env: Env | undefined): string;
161
193
  };
162
194
  /**
163
- * Constructs a {@link Cache} from `config`. The config object carries
164
- * the synchronous adapter methods (`get`/`set`/`remove`/`clear`/`keys?`)
165
- * and, optionally, a `key(context)` callback that scopes every cache
166
- * slot by the live per-`<Boundary>` Env. Omit `config` entirely for an
167
- * in-memory cache scoped to this instance.
195
+ * Constructs a {@link Cache} from `config`. The config object is a
196
+ * discriminated union of two shapes:
197
+ *
198
+ * - Adapter methods (`get`/`set`/`remove`/`keys`) plus an optional
199
+ * `key(context)`.
200
+ * - Just `key(context)` &mdash; no adapter methods at all, which falls
201
+ * back to a per-instance in-memory adapter while still scoping every
202
+ * slot by the live Env.
203
+ *
204
+ * Supplying a partial adapter (e.g. just `get` and `set`, or omitting
205
+ * `keys`) is a type error: the adapter members are an all-or-nothing
206
+ * group. Omit `config` entirely for a plain in-memory cache.
168
207
  *
169
208
  * When `key` is supplied, it runs each time the Resource layer
170
209
  * assembles a cache key, receiving the same `{ env }` shape an
@@ -175,8 +214,8 @@ export type Cache = {
175
214
  * to the loose {@link Env} record so callers that don't scope by
176
215
  * env can keep using `Cache({ ...adapter })` without supplying a
177
216
  * generic.
178
- * @param config Optional adapter-plus-options literal. Omit for an
179
- * in-memory cache; supply adapter methods alone for a persisted
180
- * cache; add `key` to also scope writes by the live Env.
217
+ * @param config Optional config literal. Omit for an in-memory cache;
218
+ * supply adapter methods for a persisted cache; supply `key` to
219
+ * scope writes by the live Env (with or without an adapter).
181
220
  */
182
- export declare function Cache<E extends object = Env>(config?: CacheConfig<E>): Cache;
221
+ export declare function Cache<E extends object = Env>(options?: CacheConfig<E>): Cache;
@@ -49,20 +49,21 @@ export type Adapter = {
49
49
  */
50
50
  readonly remove: (key: string) => void;
51
51
  /**
52
- * Wipe every entry this adapter can see. **Strictly sync.** On a
53
- * shared backend such as `localStorage` this means the whole origin
54
- * &mdash; third-party SDK state, dismissed banners, route hints, etc.
55
- * all go with it. Adapter authors should either delegate to the
56
- * backend's native clear (accepting that scope) or namespace by key
57
- * prefix and remove only their own.
52
+ * Enumerator over every key the adapter currently knows about.
53
+ * **Strictly sync.** Required &mdash; partial-match evictions
54
+ * (`resource(...).evict(where)` and `nuke(where)`) sweep these keys
55
+ * in the current tick, so an adapter that can't enumerate cannot
56
+ * support eviction. `localStorage` exposes this via
57
+ * `Object.keys(localStorage)`; MMKV via `getAllKeys()`. If your
58
+ * backend genuinely cannot enumerate (write-only audit logs, opaque
59
+ * SDK facades), implement `keys` as `() => []` to declare that
60
+ * choice explicitly and accept the no-op eviction behaviour.
61
+ *
62
+ * The Cache layer prepends every key it persists with `mh:`, so
63
+ * `keys` may return entries outside that namespace (e.g. other
64
+ * `localStorage` writes on the same origin). The wrapper filters
65
+ * before reading, removing, or clearing, so non-`mh:` keys are
66
+ * always safe &mdash; the adapter need not narrow its enumeration.
58
67
  */
59
- readonly clear: () => void;
60
- /**
61
- * Optional enumerator over every key the adapter currently knows
62
- * about. **Strictly sync** when implemented &mdash; partial-match
63
- * evictions sweep these keys in the current tick. `localStorage`
64
- * exposes this via `Object.keys(localStorage)`; MMKV via
65
- * `getAllKeys()`.
66
- */
67
- readonly keys?: () => Iterable<string>;
68
+ readonly keys: () => Iterable<string>;
68
69
  };
@@ -1,10 +1,10 @@
1
- import{jsx as e,jsxs as t}from"react/jsx-runtime";import*as n from"react";import{G as r,A as o}from"@mobily/ts-belt";import{immerable as s,enablePatches as c,Immer as i,produce as a}from"immer";function u(e){return e&&e.__esModule&&Object.prototype.hasOwnProperty.call(e,"default")?e.default:e}var l,f={exports:{}};const d=/* @__PURE__ */u((l||(l=1,function(e){var t=Object.prototype.hasOwnProperty,n="~";function r(){}function o(e,t,n){this.fn=e,this.context=t,this.once=n||!1}function s(e,t,r,s,c){if("function"!=typeof r)throw new TypeError("The listener must be a function");var i=new o(r,s||e,c),a=n?n+t:t;return e._events[a]?e._events[a].fn?e._events[a]=[e._events[a],i]:e._events[a].push(i):(e._events[a]=i,e._eventsCount++),e}function c(e,t){0===--e._eventsCount?e._events=new r:delete e._events[t]}function i(){this._events=new r,this._eventsCount=0}Object.create&&(r.prototype=/* @__PURE__ */Object.create(null),(new r).__proto__||(n=!1)),i.prototype.eventNames=function(){var e,r,o=[];if(0===this._eventsCount)return o;for(r in e=this._events)t.call(e,r)&&o.push(n?r.slice(1):r);return Object.getOwnPropertySymbols?o.concat(Object.getOwnPropertySymbols(e)):o},i.prototype.listeners=function(e){var t=this._events[n?n+e:e];if(!t)return[];if(t.fn)return[t.fn];for(var r=0,o=t.length,s=new Array(o);r<o;r++)s[r]=t[r].fn;return s},i.prototype.listenerCount=function(e){var t=this._events[n?n+e:e];return t?t.fn?1:t.length:0},i.prototype.emit=function(e,t,r,o,s,c){var i=n?n+e:e;if(!this._events[i])return!1;var a,u,l=this._events[i],f=arguments.length;if(l.fn){switch(l.once&&this.removeListener(e,l.fn,void 0,!0),f){case 1:return l.fn.call(l.context),!0;case 2:return l.fn.call(l.context,t),!0;case 3:return l.fn.call(l.context,t,r),!0;case 4:return l.fn.call(l.context,t,r,o),!0;case 5:return l.fn.call(l.context,t,r,o,s),!0;case 6:return l.fn.call(l.context,t,r,o,s,c),!0}for(u=1,a=new Array(f-1);u<f;u++)a[u-1]=arguments[u];l.fn.apply(l.context,a)}else{var d,p=l.length;for(u=0;u<p;u++)switch(l[u].once&&this.removeListener(e,l[u].fn,void 0,!0),f){case 1:l[u].fn.call(l[u].context);break;case 2:l[u].fn.call(l[u].context,t);break;case 3:l[u].fn.call(l[u].context,t,r);break;case 4:l[u].fn.call(l[u].context,t,r,o);break;default:if(!a)for(d=1,a=new Array(f-1);d<f;d++)a[d-1]=arguments[d];l[u].fn.apply(l[u].context,a)}}return!0},i.prototype.on=function(e,t,n){return s(this,e,t,n,!1)},i.prototype.once=function(e,t,n){return s(this,e,t,n,!0)},i.prototype.removeListener=function(e,t,r,o){var s=n?n+e:e;if(!this._events[s])return this;if(!t)return c(this,s),this;var i=this._events[s];if(i.fn)i.fn!==t||o&&!i.once||r&&i.context!==r||c(this,s);else{for(var a=0,u=[],l=i.length;a<l;a++)(i[a].fn!==t||o&&!i[a].once||r&&i[a].context!==r)&&u.push(i[a]);u.length?this._events[s]=1===u.length?u[0]:u:c(this,s)}return this},i.prototype.removeAllListeners=function(e){var t;return e?this._events[t=n?n+e:e]&&c(this,t):(this._events=new r,this._eventsCount=0),this},i.prototype.off=i.prototype.removeListener,i.prototype.addListener=i.prototype.on,i.prefixed=n,i.EventEmitter=i,e.exports=i}(f)),f.exports));class p extends d{cache=/* @__PURE__ */new Map;emit(e,...t){return this.cache.set(e,t[0]),super.emit(e,...t)}setCache(e,t){this.cache.set(e,t)}getCached(e){return this.cache.get(e)}fire(e,...t){return super.emit(e,...t)}}const h=n.createContext(new p);function m(){return n.useContext(h)}function y({children:t}){const r=n.useMemo(()=>new p,[]);/* @__PURE__ */
2
- return e(h.Provider,{value:r,children:t})}const b=n.createContext(/* @__PURE__ */new Set);function v({children:t}){const r=n.useMemo(()=>/* @__PURE__ */new Set,[]);/* @__PURE__ */
3
- return e(b.Provider,{value:r,children:t})}const g=n.createContext({current:{}});function w(){const e=n.useContext(g);return n.useMemo(()=>new Proxy({},{get:(t,n)=>Reflect.get(e.current,n),has:(t,n)=>n in e.current,ownKeys:()=>Reflect.ownKeys(e.current),getOwnPropertyDescriptor(t,n){const o=Object.getOwnPropertyDescriptor(e.current,n);if(!r.isUndefined(o))return{...o,configurable:!0}},set(){throw new TypeError("Env is read-only outside `context.actions.produce`. Mutate via produce(({ env }) => { env.x = ... }) instead.")}}),[e])}const P=(e="")=>`march-hare.action/${e}`,O=(e="")=>`march-hare.action/broadcast/${e}`,j=(e="")=>`march-hare.action/multicast/${e}`,S=(e="")=>`march-hare.action.lifecycle/${e}`;class E{static Payload=/* @__PURE__ */Symbol("march-hare.brand/Payload");static Broadcast=/* @__PURE__ */Symbol("march-hare.brand/Broadcast");static Multicast=/* @__PURE__ */Symbol("march-hare.brand/Multicast");static Action=/* @__PURE__ */Symbol("march-hare.brand/Action");static Channel=/* @__PURE__ */Symbol("march-hare.brand/Channel");static Name=/* @__PURE__ */Symbol("march-hare.brand/Name");static Lifecycle=/* @__PURE__ */Symbol("march-hare.brand/Lifecycle")}function x(e){const t=/* @__PURE__ */Symbol(`march-hare.action.lifecycle/${e}`),n=function(n){return{[E.Action]:t,[E.Payload]:void 0,[E.Channel]:n,[E.Name]:e,channel:n}};return Object.defineProperty(n,E.Action,{value:t,enumerable:!1}),Object.defineProperty(n,E.Payload,{value:void 0,enumerable:!1}),Object.defineProperty(n,E.Name,{value:e,enumerable:!1}),Object.defineProperty(n,E.Lifecycle,{value:e,enumerable:!1}),n}const C=Symbol(O("Fault")),N=Symbol(O("Env"));class k{static Mount(){return x("Mount")}static Paint(){return x("Paint")}static Unmount(){return x("Unmount")}static Error(){return x("Error")}static Update(){return x("Update")}static Fault=(()=>{const e={};return Object.defineProperty(e,E.Action,{value:C,enumerable:!1}),Object.defineProperty(e,E.Payload,{value:void 0,enumerable:!1}),Object.defineProperty(e,E.Broadcast,{value:!0,enumerable:!1}),Object.defineProperty(e,E.Name,{value:"Fault",enumerable:!1}),e})();static Env=(()=>{const e={};return Object.defineProperty(e,E.Action,{value:N,enumerable:!1}),Object.defineProperty(e,E.Payload,{value:void 0,enumerable:!1}),Object.defineProperty(e,E.Broadcast,{value:!0,enumerable:!1}),Object.defineProperty(e,E.Name,{value:"Env",enumerable:!1}),e})()}var M=/* @__PURE__ */(e=>(e.Unicast="unicast",e.Broadcast="broadcast",e.Multicast="multicast",e))(M||{}),A=/* @__PURE__ */(e=>(e.Mounting="mounting",e.Mounted="mounted",e.Unmounting="unmounting",e.Unmounted="unmounted",e))(A||{});function _({initial:t,children:o}){const s=n.useRef(t),c=m();return r.isUndefined(c.getCached(N))&&c.setCache(N,s.current),/* @__PURE__ */e(g.Provider,{value:s,children:o})}const R=n.createContext(/* @__PURE__ */new WeakMap);function U({children:t}){const r=n.useMemo(()=>/* @__PURE__ */new WeakMap,[]);/* @__PURE__ */
1
+ import{jsx as e,jsxs as t}from"react/jsx-runtime";import*as n from"react";import{G as r,A as o}from"@mobily/ts-belt";import{immerable as s,enablePatches as c,Immer as i,produce as a}from"immer";function u(e){return e&&e.__esModule&&Object.prototype.hasOwnProperty.call(e,"default")?e.default:e}var l,f={exports:{}};const d=/* @__PURE__ */u((l||(l=1,function(e){var t=Object.prototype.hasOwnProperty,n="~";function r(){}function o(e,t,n){this.fn=e,this.context=t,this.once=n||!1}function s(e,t,r,s,c){if("function"!=typeof r)throw new TypeError("The listener must be a function");var i=new o(r,s||e,c),a=n?n+t:t;return e._events[a]?e._events[a].fn?e._events[a]=[e._events[a],i]:e._events[a].push(i):(e._events[a]=i,e._eventsCount++),e}function c(e,t){0===--e._eventsCount?e._events=new r:delete e._events[t]}function i(){this._events=new r,this._eventsCount=0}Object.create&&(r.prototype=/* @__PURE__ */Object.create(null),(new r).__proto__||(n=!1)),i.prototype.eventNames=function(){var e,r,o=[];if(0===this._eventsCount)return o;for(r in e=this._events)t.call(e,r)&&o.push(n?r.slice(1):r);return Object.getOwnPropertySymbols?o.concat(Object.getOwnPropertySymbols(e)):o},i.prototype.listeners=function(e){var t=this._events[n?n+e:e];if(!t)return[];if(t.fn)return[t.fn];for(var r=0,o=t.length,s=new Array(o);r<o;r++)s[r]=t[r].fn;return s},i.prototype.listenerCount=function(e){var t=this._events[n?n+e:e];return t?t.fn?1:t.length:0},i.prototype.emit=function(e,t,r,o,s,c){var i=n?n+e:e;if(!this._events[i])return!1;var a,u,l=this._events[i],f=arguments.length;if(l.fn){switch(l.once&&this.removeListener(e,l.fn,void 0,!0),f){case 1:return l.fn.call(l.context),!0;case 2:return l.fn.call(l.context,t),!0;case 3:return l.fn.call(l.context,t,r),!0;case 4:return l.fn.call(l.context,t,r,o),!0;case 5:return l.fn.call(l.context,t,r,o,s),!0;case 6:return l.fn.call(l.context,t,r,o,s,c),!0}for(u=1,a=new Array(f-1);u<f;u++)a[u-1]=arguments[u];l.fn.apply(l.context,a)}else{var d,h=l.length;for(u=0;u<h;u++)switch(l[u].once&&this.removeListener(e,l[u].fn,void 0,!0),f){case 1:l[u].fn.call(l[u].context);break;case 2:l[u].fn.call(l[u].context,t);break;case 3:l[u].fn.call(l[u].context,t,r);break;case 4:l[u].fn.call(l[u].context,t,r,o);break;default:if(!a)for(d=1,a=new Array(f-1);d<f;d++)a[d-1]=arguments[d];l[u].fn.apply(l[u].context,a)}}return!0},i.prototype.on=function(e,t,n){return s(this,e,t,n,!1)},i.prototype.once=function(e,t,n){return s(this,e,t,n,!0)},i.prototype.removeListener=function(e,t,r,o){var s=n?n+e:e;if(!this._events[s])return this;if(!t)return c(this,s),this;var i=this._events[s];if(i.fn)i.fn!==t||o&&!i.once||r&&i.context!==r||c(this,s);else{for(var a=0,u=[],l=i.length;a<l;a++)(i[a].fn!==t||o&&!i[a].once||r&&i[a].context!==r)&&u.push(i[a]);u.length?this._events[s]=1===u.length?u[0]:u:c(this,s)}return this},i.prototype.removeAllListeners=function(e){var t;return e?this._events[t=n?n+e:e]&&c(this,t):(this._events=new r,this._eventsCount=0),this},i.prototype.off=i.prototype.removeListener,i.prototype.addListener=i.prototype.on,i.prefixed=n,i.EventEmitter=i,e.exports=i}(f)),f.exports));class h extends d{cache=/* @__PURE__ */new Map;latest=/* @__PURE__ */new Map;emit(e,...t){return this.setCache(e,t[0],void 0),super.emit(e,...t)}setCache(e,t,n){const r=this.cache.get(e)??/* @__PURE__ */new Map,o={channel:n,value:t};r.set(function(e){return void 0===e?"":JSON.stringify(e)}(n),o),this.cache.set(e,r),this.latest.set(e,o)}getCached(e){return this.latest.get(e)?.value}getCachedAll(e){return this.cache.get(e)?.values()??[]}fire(e,...t){return super.emit(e,...t)}}const p=n.createContext(new h);function m(){return n.useContext(p)}function y({children:t}){const r=n.useMemo(()=>new h,[]);/* @__PURE__ */
2
+ return e(p.Provider,{value:r,children:t})}const v=n.createContext(/* @__PURE__ */new Set);function b({children:t}){const r=n.useMemo(()=>/* @__PURE__ */new Set,[]);/* @__PURE__ */
3
+ return e(v.Provider,{value:r,children:t})}const g=n.createContext({current:{}});function w(){const e=n.useContext(g);return n.useMemo(()=>new Proxy({},{get:(t,n)=>Reflect.get(e.current,n),has:(t,n)=>n in e.current,ownKeys:()=>Reflect.ownKeys(e.current),getOwnPropertyDescriptor(t,n){const o=Object.getOwnPropertyDescriptor(e.current,n);if(!r.isUndefined(o))return{...o,configurable:!0}},set(){throw new TypeError("Env is read-only outside `context.actions.produce`. Mutate via produce(({ env }) => { env.x = ... }) instead.")}}),[e])}const O=(e="")=>`march-hare.action/${e}`,P=(e="")=>`march-hare.action/broadcast/${e}`,j=(e="")=>`march-hare.action/multicast/${e}`,S=(e="")=>`march-hare.action.lifecycle/${e}`;class E{static Payload=/* @__PURE__ */Symbol("march-hare.brand/Payload");static Broadcast=/* @__PURE__ */Symbol("march-hare.brand/Broadcast");static Multicast=/* @__PURE__ */Symbol("march-hare.brand/Multicast");static Action=/* @__PURE__ */Symbol("march-hare.brand/Action");static Channel=/* @__PURE__ */Symbol("march-hare.brand/Channel");static Name=/* @__PURE__ */Symbol("march-hare.brand/Name");static Lifecycle=/* @__PURE__ */Symbol("march-hare.brand/Lifecycle")}function x(e){const t=/* @__PURE__ */Symbol(`march-hare.action.lifecycle/${e}`),n=function(n){return{[E.Action]:t,[E.Payload]:void 0,[E.Channel]:n,[E.Name]:e,channel:n}};return Object.defineProperty(n,E.Action,{value:t,enumerable:!1}),Object.defineProperty(n,E.Payload,{value:void 0,enumerable:!1}),Object.defineProperty(n,E.Name,{value:e,enumerable:!1}),Object.defineProperty(n,E.Lifecycle,{value:e,enumerable:!1}),n}const C=Symbol(P("Fault")),M=Symbol(P("Env"));class k{static Mount(){return x("Mount")}static Paint(){return x("Paint")}static Unmount(){return x("Unmount")}static Error(){return x("Error")}static Update(){return x("Update")}static Fault=(()=>{const e={};return Object.defineProperty(e,E.Action,{value:C,enumerable:!1}),Object.defineProperty(e,E.Payload,{value:void 0,enumerable:!1}),Object.defineProperty(e,E.Broadcast,{value:!0,enumerable:!1}),Object.defineProperty(e,E.Name,{value:"Fault",enumerable:!1}),e})();static Env=(()=>{const e={};return Object.defineProperty(e,E.Action,{value:M,enumerable:!1}),Object.defineProperty(e,E.Payload,{value:void 0,enumerable:!1}),Object.defineProperty(e,E.Broadcast,{value:!0,enumerable:!1}),Object.defineProperty(e,E.Name,{value:"Env",enumerable:!1}),e})()}var N=/* @__PURE__ */(e=>(e.Unicast="unicast",e.Broadcast="broadcast",e.Multicast="multicast",e))(N||{}),A=/* @__PURE__ */(e=>(e.Mounting="mounting",e.Mounted="mounted",e.Unmounting="unmounting",e.Unmounted="unmounted",e))(A||{});function _({initial:t,children:o}){const s=n.useRef(t),c=m();return r.isUndefined(c.getCached(M))&&c.setCache(M,s.current,void 0),/* @__PURE__ */e(g.Provider,{value:s,children:o})}const R=n.createContext(/* @__PURE__ */new WeakMap);function U({children:t}){const r=n.useMemo(()=>/* @__PURE__ */new WeakMap,[]);/* @__PURE__ */
4
4
  return e(R.Provider,{value:r,children:t})}const L=n.createContext(()=>{});function W({tap:t,children:r}){const o=n.useRef(t);n.useLayoutEffect(()=>{o.current=t},[t]);const s=n.useMemo(()=>e=>o.current?.(e),[]);/* @__PURE__ */
5
5
  return e(L.Provider,{value:s,children:r})}const B=n.createContext(/* @__PURE__ */new Map);function $({env:t,tap:r,children:o}){const s=n.useMemo(()=>/* @__PURE__ */new Map,[]);/* @__PURE__ */
6
- return e(y,{children:/* @__PURE__ */e(B.Provider,{value:s,children:/* @__PURE__ */e(_,{initial:t??{},children:/* @__PURE__ */e(v,{children:/* @__PURE__ */e(W,{tap:r,children:/* @__PURE__ */e(U,{children:o})})})})})})}const T=e=>"symbol"==typeof e;function F(e){return r.isString(e)||T(e)?e:(r.isObject(e)||r.isFunction(e))&&E.Action in e?e[E.Action]:e}function z(e){if(r.isString(e))return e.startsWith(O());if(T(e))return e.description?.startsWith(O())??!1;if(r.isObject(e)||r.isFunction(e)){if(E.Broadcast in e&&e[E.Broadcast])return!0;if(E.Action in e){const t=e[E.Action];return t.description?.startsWith(O())??!1}}return!1}function D(e){return r.isObject(e)&&E.Channel in e&&"channel"in e}function H(e){const t=F(e),n=T(t)?t.description??"":t;return n.startsWith(S())&&n.slice(S().length)||null}function I(e){if(r.isString(e))return e.startsWith(j());if(T(e))return e.description?.startsWith(j())??!1;if(r.isObject(e)||r.isFunction(e)){if(E.Multicast in e&&e[E.Multicast])return!0;if(E.Action in e){const t=e[E.Action];return t.description?.startsWith(j())??!1}}return!1}const J=(e="",t=M.Unicast)=>{const n=t===M.Broadcast?Symbol(O(e)):t===M.Multicast?Symbol(j(e)):Symbol(P(e)),r=function(t){return{[E.Action]:n,[E.Payload]:void 0,[E.Channel]:t,[E.Name]:e,channel:t}};return Object.defineProperty(r,E.Action,{value:n,enumerable:!1}),Object.defineProperty(r,E.Payload,{value:void 0,enumerable:!1}),Object.defineProperty(r,E.Name,{value:e,enumerable:!1}),t===M.Broadcast&&Object.defineProperty(r,E.Broadcast,{value:!0,enumerable:!1}),t===M.Multicast&&Object.defineProperty(r,E.Multicast,{value:!0,enumerable:!1}),r},G=Symbol(((e="")=>`march-hare/replay${e}`)());function K(e,t,...n){e instanceof p&&e.setCache(t,n[0]);const r=e.listeners(t);return 0===r.length?Promise.resolve():Promise.all(r.map(e=>Promise.resolve(e(...n)))).then(()=>{})}function V(e,t){for(const n of e.keys())if(H(n)===t)return n;return null}const q=/* @__PURE__ */Symbol("march-hare.unset");function Q(){const[,e]=n.useReducer(e=>e+1,0);return e}function X(){return{data:q,at:null}}function Y(e,t){return{data:e,at:t}}var Z=/* @__PURE__ */(e=>(e[e.Aborted=0]="Aborted",e[e.Errored=1]="Errored",e))(Z||{});class ee extends Error{name="AbortError";constructor(e="Aborted"){super(e)}}const te=n.createContext(null);function ne(e){const t=r.isUndefined(e)?function(){const e=/* @__PURE__ */new Map;return{get:t=>e.get(t)??null,set:(t,n)=>{e.set(t,n)},remove:t=>{e.delete(t)},clear:()=>{e.clear()},keys:()=>e.keys()}}():e,n=e?.key;return{get(e){try{const n=t.get(e);if(r.isNull(n))return X();const o=JSON.parse(n);return Y(o.data,Temporal.Instant.from(o.at))}catch{return X()}},set(e,n){if(n.data!==q&&!r.isNull(n.at))try{t.set(e,JSON.stringify({data:n.data,at:n.at.toString()}))}catch{return}},remove(e){try{t.remove(e)}catch{return}},clear(){try{t.clear()}catch{return}},keys(){try{return t.keys?.()??[]}catch{return[]}},scope(e){if(r.isUndefined(n)||r.isNullable(e))return"";try{const t=n({env:e});return r.isNullable(t)?"":t}catch{return""}}}}const re=/* @__PURE__ */new WeakMap,oe=/* @__PURE__ */new Map,se=[];function ce(e,t,n,o){const s=r.isNull(n)?"":`${n}:`,c=(e,n)=>{const r=t.scope(e);return`${""===r?"":`${r}:`}${s}${function(e){return JSON.stringify(e)}(n)}`},i=(e,n)=>{const o=t.get(c(n,e));return o.data===q||r.isNull(o.at)?{data:q,at:null}:{data:o.data,at:o.at}},a=(n,r,o,s)=>e({env:n,controller:r,params:o,dispatch:s}).then(e=>(t.set(c(n,o),Y(e,Temporal.Now.instant())),e)),u=e=>{const n=o(),r=t.scope(n),c=""===r?s:`${r}:${s}`,i=Object.entries(e);for(const o of[...t.keys()])if(o.startsWith(c))try{const e=JSON.parse(o.slice(c.length));i.every(([t,n])=>e[t]===n)&&t.remove(o)}catch{continue}};function l(e){return{run:a,read:e=>i(e,o()),evict:u,params:e??{}}}return se.push(u),Object.defineProperty(l,"get",{value:function(e){const{data:t}=i(e??{},o());return t===q?null:t},enumerable:!1}),l}function ie(e,t,n){const o=e,s=n??(()=>{});return r.isUndefined(t)?ce(o,function(e){const t=re.get(e);if(r.isNotNullable(t))return t;const n=ne();return re.set(e,n),n}(o),null,s):ce(o,t,function(e){const t=oe.get(e);if(r.isNotNullable(t))return t;const n=String(oe.size);return oe.set(e,n),n}(o),s)}let ae=(e=21)=>{let t="",n=crypto.getRandomValues(new Uint8Array(e|=0));for(;e--;)t+="useandom-26T198340PX75pxJACKVERYMINDBUSHWOLF_GQZbfghjklqvwyzrict"[63&n[e]];return t};var ue=/* @__PURE__ */(e=>(e[e.Add=1]="Add",e[e.Remove=2]="Remove",e[e.Update=4]="Update",e[e.Move=8]="Move",e[e.Replace=16]="Replace",e[e.Sort=32]="Sort",e[e.Create=64]="Create",e[e.Fetch=128]="Fetch",e[e.Clone=256]="Clone",e[e.Archive=512]="Archive",e[e.Restore=1024]="Restore",e[e.Merge=2048]="Merge",e[e.Reorder=4096]="Reorder",e[e.Sync=8192]="Sync",e[e.Publish=16384]="Publish",e[e.Link=32768]="Link",e[e.Unlink=65536]="Unlink",e[e.Lock=131072]="Lock",e[e.Unlock=262144]="Unlock",e[e.Import=524288]="Import",e[e.Export=1048576]="Export",e[e.Transfer=2097152]="Transfer",e))(ue||{}),le=/* @__PURE__ */(e=>(e[e.Produce=0]="Produce",e[e.Hydrate=1]="Hydrate",e))(le||{}),fe=/* @__PURE__ */(e=>(e.Property="property",e.Process="process",e.Value="value",e.Operation="operation",e))(fe||{});class de{[s]=!0;static keys=new Set(Object.values(fe));property=null;process=null;value;operation;constructor(e,t){this.value=e,this.operation=t}assign(e,t){const n=new de(this.value,this.operation);return n.property=e,n.process=t,n}}class pe{static immer=(()=>{c();const e=new i;return e.setAutoFreeze(!1),e})();static tag="κ";static id=ae}const he=/* @__PURE__ */Symbol("Box");function me(e,t){const n="string"==typeof t?""===t?[]:t.split("."):t;let r=e;for(const o of n){if(null==r)return;r=r[o]}return r}function ye(e){if(r.isNullable(e)||ge(e))return e;if(r.isArray(e))return e.map(e=>ye(e));if(r.isObject(e)&&ve(e)){const t=Object.entries(e).map(([e,t])=>[e,ye(t)]);return{...Object.fromEntries(t),[pe.tag]:e[pe.tag]??pe.id()}}return e}function be(e){if(Array.isArray(e))return e.filter(e=>pe.tag in e).map(e=>e[pe.tag]??"").join(",");const t=e[pe.tag];if(t)return t;try{return JSON.stringify(e)}catch{return`[unserializable:${typeof e}]`}}function ve(e){const t=Object.getPrototypeOf(e);return t===Object.prototype||null===t}function ge(e){return r.isNullable(e)||r.isString(e)||r.isNumber(e)||r.isBoolean(e)||"symbol"==typeof e||"bigint"==typeof e}function we(e){return r.isObject(e)&&he in e}function Pe(e,t,n,o,s,c){return function i(a,u=t.path){if(a instanceof de){const t=me(n,u.join("."));if(Object.entries(a).filter(([e,t])=>!de.keys.has(e)&&t instanceof de).forEach(([e,t])=>i(t,u.concat(e))),ge(a.value)){if(e===le.Hydrate)return a.value;const i=u.slice(0,-1),l=i.length>0?me(n,i.join(".")):n;return r.isNullable(l)||Oe(l,a,u.at(-1),o,s,c),t??a.value}if(e===le.Hydrate){const e=ye(i(a.value,u));return Oe(e,a,null,o,s,c),e}const l=t??ye(a.value);return Oe(l,a,null,o,s,c),r.isNullable(t)?l:(i(a.value,u),t)}if(r.isArray(a))return a.map((e,t)=>i(e,u.concat(t)));if(r.isObject(a)&&!ve(a))return a;if(r.isObject(a)){const t=Object.entries(a).map(([e,t])=>[e,i(t,u.concat(e))]),n=Object.fromEntries(t);if(e===le.Hydrate){const e=ye(n);return Object.entries(a).forEach(([t,n])=>{n instanceof de&&ge(n.value)&&Oe(e,n,t,o,s,c)}),e}return n}return a}(t.value)}function Oe(e,t,n,r,o,s){const c=s(e),i=o.get(c)??[];o.set(c,[t.assign(n,r),...i])}class je{#e={};#t;#n=/* @__PURE__ */new Map;#r=/* @__PURE__ */new Set;#o=!1;constructor(e=be){this.#t=e}static pk(){return ae()}static"κ"=je.pk;annotate(e,t){return new de(t,e)}"δ"=this.annotate;get model(){return this.#e}get inspect(){return function(e,t,n,s,c){function i(s){const c=s.at(-1),i=me(e(),s),a=s.slice(0,-1),u=o.isNotEmpty(a)?me(e(),a):e();return[...r.isObject(i)||r.isArray(i)?t.get(n(i))?.filter(e=>r.isNullable(e.property))??[]:[],...r.isObject(u)?t.get(n(u))?.filter(e=>e.property===c)??[]:[]]}return function t(n){return new Proxy(()=>{},{get:(r,a)=>"pending"===a?()=>!o.isEmpty(i(n)):"remaining"===a?()=>o.length(i(n)):"box"===a?()=>({value:me(e(),n),inspect:t(n),[he]:!0}):"is"===a?e=>i(n).some(t=>0!==(t.operation&e)):"draft"===a?()=>o.head(i(n))?.value??me(e(),n):"settled"===a?()=>new Promise(t=>{if(o.isEmpty(i(n)))return t(me(e(),n));const r=()=>{o.isEmpty(i(n))&&(c(r),t(me(e(),n)))};s(r)}):t([...n,String(a)])})}([])}(()=>this.#e,this.#n,this.#t,e=>this.#r.add(e),e=>this.#r.delete(e))}hydrate(e){return this.#o=!0,this.#s(le.Hydrate,()=>e)}produce(e){if(!this.#o)throw new Error("State must be hydrated using hydrate() before calling produce()");return this.#s(le.Produce,e)}#s(e,t){const n=/* @__PURE__ */Symbol("process"),[,r]=pe.immer.produceWithPatches(this.#e,t);return this.#e=r.reduce((t,r)=>pe.immer.applyPatches(t,[{...r,value:Pe(e,r,t,n,this.#n,this.#t)}]),this.#e),this.#e=ye(this.#e),this.#c(),n}prune(e){this.#n.forEach((t,n)=>{const r=t.filter(t=>t.process!==e);o.isEmpty(r)?this.#n.delete(n):this.#n.set(n,r)}),this.#c()}#c(){this.#r.forEach(e=>e())}observe(e){const t=()=>e(this.#e);return this.#r.add(t),()=>this.#r.delete(t)}}function Se({action:e,renderer:t}){const o=m(),s=n.useContext(B),c=Q(),i=n.useMemo(()=>{const t=s.get(e);if(t)return t;const n=new je,c=o.getCached(e);r.isNotNullable(c)&&n.hydrate({value:c});const i={state:n,listeners:/* @__PURE__ */new Set};return s.set(e,i),i},[e,o,s]);n.useLayoutEffect(()=>{function t(e){i.state.hydrate({value:e}),i.listeners.forEach(e=>e())}return i.listeners.add(c),o.on(e,t),()=>{i.listeners.delete(c),o.off(e,t)}},[e,o,i]);const a=i.state.model?.value;return r.isNullable(a)?null:t(a,i.state.inspect.value)}function Ee(e,t){const n=t.split(".");let r=e;for(let o=0;o<n.length-1;o++)r=r[n[o]];return{cursor:r,key:n[n.length-1]}}function xe(e,t,n){const{cursor:r,key:o}=Ee(e,t);r[o]=n}function Ce(e){return(t,n)=>{t.actions.produce(t=>{xe(t.model,e,n)})}}function Ne(e){return t=>{t.actions.produce(t=>{!function(e,t){const{cursor:n,key:r}=Ee(e,t);n[r]=!n[r]}(t.model,e)})}}function ke(e,t){return n=>{n.actions.produce(n=>{xe(n.model,e,t)})}}function Me(){const e=n.useRef(null);return n.useMemo(()=>({actions:{dispatch:function(t,n){const r=e.current;if(!r)throw new Error("march-hare: useContext handle dispatched before its paired context.useActions(...) ran. Call context.actions.dispatch from event handlers, not synchronously during render.");return r(t,n)}},useActions:function(...t){const s=function(...e){const t=r.isUndefined(e[0])||r.isFunction(e[0])?{}:e[0],s=r.isFunction(e[0])?e[0]:e[1]??(()=>({})),c=m(),i=n.useContext(te),u=n.useContext(b),l=w(),f=n.useContext(g),p=n.useContext(R),h=n.useContext(L),y=Q(),v=n.useRef(!1),O=n.useRef(null),j=n.useRef(new je);v.current||(v.current=!0,O.current=j.current.hydrate(t));const[S,E]=n.useState(()=>j.current.model),x=function(e){const t=n.useRef(e);return t.current=e,n.useMemo(()=>{return n=t,Object.keys(e).reduce((e,t)=>(Object.defineProperty(e,t,{get:()=>n.current[t],enumerable:!0}),e),{});var n},[e])}(s()),k=n.useMemo(()=>new d,[]),M=n.useRef({handlers:/* @__PURE__ */new Map});M.current.handlers=/* @__PURE__ */new Map;const _=function(){const e=n.useRef(/* @__PURE__ */new Set),t=n.useRef(/* @__PURE__ */new Set);return n.useMemo(()=>({broadcast:e.current,multicast:t.current}),[])}(),U=n.useRef(A.Mounting),W=n.useRef(/* @__PURE__ */new Set),B=n.useRef(0),$=n.useCallback((e,t,n)=>{const o=new AbortController,s={controller:o,action:e,payload:t};return u.add(s),W.current.add(s),{get model(){return j.current.model},get phase(){return U.current},task:s,data:x,tasks:u,env:l,actions:{produce(e){if(o.signal.aborted)return;const t=f.current,r=j.current.produce(t=>{f.current=a(f.current,n=>{e({model:t,inspect:j.current.inspect,env:n})})});E(j.current.model),f.current!==t&&c.emit(N,f.current),n.processes.add(r),O.current&&(n.processes.add(O.current),O.current=null)},dispatch(e,t){if(o.signal.aborted)return Promise.resolve();const n=F(e),r=D(e)?e.channel:void 0;return I(e)?i?K(i.emitter,n,t,r):Promise.resolve():K(z(e)?c:k,n,t,r)},annotate:(e,t=ue.Update)=>j.current.annotate(t,e),get inspect(){return j.current.inspect},resource:Object.assign(function(e){const t=(e,t)=>{if(o.signal.aborted)return Promise.resolve();const n=e,r=F(n);return I(n)?i?K(i.emitter,r,t,void 0):Promise.resolve():z(n)?K(c,r,t,void 0):Promise.resolve()},n={exceedsWindow:null,isolated:!1},s={then:(s,c)=>(()=>{if(r.isNotNullable(n.exceedsWindow)){const{data:t,at:o}=e.read(e.params);if(t!==q&&r.isNotNullable(o)){const e=Temporal.Now.instant().since(o),r=Temporal.Duration.from(n.exceedsWindow);if(Temporal.Duration.compare(e,r)<=0)return Promise.resolve(t)}}if(n.isolated)return e.run(l,o,e.params,t);let s=p.get(e.run);r.isUndefined(s)&&(s=/* @__PURE__ */new Map,p.set(e.run,s));const c=s,i=JSON.stringify(e.params);let a=c.get(i);if(r.isUndefined(a)){const n=new AbortController,r={controller:n,refs:0};r.promise=e.run(l,n,e.params,t).finally(()=>{c.delete(i)}),c.set(i,r),a=r}const u=a;u.refs+=1;const f=()=>{u.refs-=1,0===u.refs&&(c.delete(i),u.controller.abort(o.signal.reason))};if(o.signal.aborted)f();else{o.signal.addEventListener("abort",f,{once:!0});const e=()=>o.signal.removeEventListener("abort",f);u.promise.then(e,e)}return d=u.promise,h=o.signal,new Promise((e,t)=>{if(h.aborted)return void t(h.reason);const n=()=>t(h.reason);h.addEventListener("abort",n,{once:!0}),d.then(t=>{h.removeEventListener("abort",n),e(t)},e=>{h.removeEventListener("abort",n),t(e)})});var d,h})().then(s,c),exceeds:e=>(n.exceedsWindow=e,s),isolated:()=>(n.isolated=!0,s),evict(t){e.evict(t??e.params)}};return s},{nuke:e=>function(e){const t=e??{};for(const n of se)n(t)}(e)}),async final(e){if(o.signal.aborted)return null;const t=F(e),n=I(e)?i?.emitter??null:c;if(!n)return null;const s=n.getCached(t);if(r.isUndefined(s))return null;const a=j.current.inspect;return a.pending()&&await new Promise((e,t)=>{if(o.signal.aborted)return void t(o.signal.reason);const n=()=>t(o.signal.reason);o.signal.addEventListener("abort",n,{once:!0}),a.settled().then(()=>{o.signal.removeEventListener("abort",n),e()})}),n.getCached(t)??null},peek(e){if(o.signal.aborted)return null;const t=F(e),n=I(e)?i?.emitter??null:c;return n?n.getCached(t)??null:null}}}},[S]);n.useLayoutEffect(()=>{function e(e,t,n){return function(o,s){const a=n();if(s===G&&r.isNotNullable(a))return;if(r.isNotNullable(s)&&s!==G&&r.isNotNullable(a)&&!function(e,t){for(const n of Object.keys(e))if(t[n]!==e[n])return!1;return!0}(s,a))return;const l={processes:/* @__PURE__ */new Set},d=Promise.withResolvers(),p=$(e,o,l),m=function(e){const t=F(e),n=r.isString(t)?t:t.description??"";return n.startsWith(P())&&n.slice(n.lastIndexOf("/")+1)||"unknown"}(e),b=performance.now(),v=j.current.model,g=f.current;let w,O=!1;function S(){const e=j.current.model,t=f.current;return{model:v===e?null:{before:v,after:e},env:g===t?null:{before:g,after:t}}}function E(){const t=s===G?void 0:s;return I(e)?i?K(i.emitter,e,o,t):Promise.resolve():K(z(e)?c:k,e,o,t)}function x(e){O=!0;const t=V(M.current.handlers,"Error"),n=r.isNotNullable(t),s=function(e){return e instanceof Error&&"AbortError"===e.name?Z.Aborted:Z.Errored}(e),i=function(e){return e instanceof Error?e:new Error(String(e))}(e),a={reason:s,error:i,action:m,handled:n,tasks:u,retry:E};c.fire(C,a),n&&t&&k.emit(t,a),h({stage:"end",result:"error",action:{name:m,payload:o},details:{task:p.task,elapsed:performance.now()-b,mutations:S(),error:i,reason:s}})}function N(){for(const e of u)if(e===p.task){u.delete(e),W.current.delete(e);break}l.processes.forEach(e=>j.current.prune(e)),l.processes.size>0&&y(),O||h({stage:"end",result:"success",action:{name:m,payload:o},details:{task:p.task,elapsed:performance.now()-b,mutations:S()}}),d.resolve()}h({stage:"start",action:{name:m,payload:o},details:{task:p.task}});try{w=t(p,o)}catch(A){return x(A),N(),d.promise}return function(e){if(!e||"object"!=typeof e)return!1;const t=Object.prototype.toString.call(e);return"[object Generator]"===t||"[object AsyncGenerator]"===t}(w)?((async()=>{for await(const e of w);})().catch(x).finally(N),d.promise):(Promise.resolve(w).catch(x).finally(N),d.promise)}}B.current++;const t=/* @__PURE__ */new Set;return M.current.handlers.forEach((n,r)=>{for(const{getChannel:o,handler:s}of n){const n=e(r,s,o);if(I(r)){if(i){const e=i.emitter;e.on(r,n),t.add(()=>e.off(r,n))}k.on(r,n),_.multicast.add(r),t.add(()=>k.off(r,n))}else z(r)?(c.on(r,n),k.on(r,n),_.broadcast.add(r),t.add(()=>{c.off(r,n),k.off(r,n)})):(k.on(r,n),t.add(()=>k.off(r,n)))}}),()=>{const e=++B.current,n=new Set(t);queueMicrotask(()=>{if(B.current!==e){for(const e of n)e();return}for(const e of W.current)e.controller.abort(new ee("Component unmounted")),u.delete(e);W.current.clear(),U.current=A.Unmounting;const t=V(M.current.handlers,"Unmount");t&&k.emit(t),U.current=A.Unmounted;for(const e of n)e()})}},[k]),function({unicast:e,broadcast:t,dispatchers:s,scope:c,phase:i,data:a,handlers:u}){const l=n.useRef(null),f=n.useRef(!1);n.useLayoutEffect(()=>{if(i.current===A.Mounted)return;i.current=A.Mounting;const n=V(u,"Mount");n&&e.emit(n),s.broadcast.forEach(n=>{const o=t.getCached(n);r.isNullable(o)||e.emit(n,o,G)}),c&&s.multicast.forEach(t=>{const n=c.emitter.getCached(t);r.isNullable(n)||e.emit(t,n,G)}),i.current=A.Mounted,f.current=!1},[]),n.useEffect(()=>{if(f.current)return;f.current=!0;const t=V(u,"Paint");t&&e.emit(t)},[]),n.useLayoutEffect(()=>{if(r.isNotNullable(l.current)){const t=function(e,t){return Object.keys(t).reduce((n,r)=>e[r]!==t[r]?{...n,[r]:t[r]}:n,{})}(l.current,a);if(o.isNotEmpty(Object.keys(t))){const n=V(u,"Update");n&&e.emit(n,t)}}l.current=a},[a,e])}({unicast:k,broadcast:c,dispatchers:_,scope:i,phase:U,data:s(),handlers:M.current.handlers});const T=n.useMemo(()=>({dispatch(e,t){const n=F(e),r=D(e)?e.channel:void 0;return I(e)?i?K(i.emitter,n,t,r):Promise.resolve():K(z(e)?c:k,n,t,r)},get inspect(){return j.current.inspect},stream:(e,t)=>n.createElement(Se,{action:F(e),renderer:t})}),[S,k]),H=n.useMemo(()=>[S,T,x],[S,T,x]);return H.useAction=(e,t)=>{!function(e,t,r){const o=n.useRef(r);n.useLayoutEffect(()=>{o.current=r});const s=n.useRef(t);n.useLayoutEffect(()=>{s.current=t});const c=n.useCallback((e,t)=>o.current(e,t),[]),i=n.useCallback(()=>D(s.current)?s.current.channel:void 0,[]),a=F(t),u=e.current.handlers.get(a)??/* @__PURE__ */new Set;0===u.size&&e.current.handlers.set(a,u),u.add({getChannel:i,handler:c})}(M,e,t)},H.dispatch=H[1].dispatch,H}(...t);return e.current=s.dispatch,s},with:{update:e=>Ce(e),invert:e=>Ne(e),always:(e,t)=>ke(e,t)}}),[])}function Ae(t,r){return{Boundary:function({children:t}){const r=n.useMemo(()=>({id:/* @__PURE__ */Symbol("march-hare.scope/instance"),emitter:new p}),[]);/* @__PURE__ */
7
- return e(te.Provider,{value:r,children:t})},useContext:function(){return Me()},useEnv:function(){return w()},Resource:function(e){return ie(e,t,r)}}}function _e(n){const r={current:void 0};return{Boundary:function({children:o}){/* @__PURE__ */
6
+ return e(y,{children:/* @__PURE__ */e(B.Provider,{value:s,children:/* @__PURE__ */e(_,{initial:t??{},children:/* @__PURE__ */e(b,{children:/* @__PURE__ */e(W,{tap:r,children:/* @__PURE__ */e(U,{children:o})})})})})})}const T=e=>"symbol"==typeof e;function F(e){return r.isString(e)||T(e)?e:(r.isObject(e)||r.isFunction(e))&&E.Action in e?e[E.Action]:e}function z(e){if(r.isString(e))return e.startsWith(P());if(T(e))return e.description?.startsWith(P())??!1;if(r.isObject(e)||r.isFunction(e)){if(E.Broadcast in e&&e[E.Broadcast])return!0;if(E.Action in e){const t=e[E.Action];return t.description?.startsWith(P())??!1}}return!1}function J(e){return r.isObject(e)&&E.Channel in e&&"channel"in e}function D(e){const t=F(e),n=T(t)?t.description??"":t;return n.startsWith(S())&&n.slice(S().length)||null}function H(e){if(r.isString(e))return e.startsWith(j());if(T(e))return e.description?.startsWith(j())??!1;if(r.isObject(e)||r.isFunction(e)){if(E.Multicast in e&&e[E.Multicast])return!0;if(E.Action in e){const t=e[E.Action];return t.description?.startsWith(j())??!1}}return!1}const I=(e="",t=N.Unicast)=>{const n=t===N.Broadcast?Symbol(P(e)):t===N.Multicast?Symbol(j(e)):Symbol(O(e)),r=function(t){return{[E.Action]:n,[E.Payload]:void 0,[E.Channel]:t,[E.Name]:e,channel:t}};return Object.defineProperty(r,E.Action,{value:n,enumerable:!1}),Object.defineProperty(r,E.Payload,{value:void 0,enumerable:!1}),Object.defineProperty(r,E.Name,{value:e,enumerable:!1}),t===N.Broadcast&&Object.defineProperty(r,E.Broadcast,{value:!0,enumerable:!1}),t===N.Multicast&&Object.defineProperty(r,E.Multicast,{value:!0,enumerable:!1}),r};function G(e,t,...n){e instanceof h&&e.setCache(t,n[0],n[1]);const r=e.listeners(t);return 0===r.length?Promise.resolve():Promise.all(r.map(e=>Promise.resolve(e(...n)))).then(()=>{})}function K(e,t){for(const n of e.keys())if(D(n)===t)return n;return null}const V=/* @__PURE__ */Symbol("march-hare.unset"),q="mh:";function Q(){const[,e]=n.useReducer(e=>e+1,0);return e}function X(){return{data:V,at:null}}function Y(e,t){return{data:e,at:t}}var Z=/* @__PURE__ */(e=>(e[e.Aborted=0]="Aborted",e[e.Errored=1]="Errored",e))(Z||{});class ee extends Error{name="AbortError";constructor(e="Aborted"){super(e)}}const te=n.createContext(null);function ne(e){const t=function(e){return!r.isUndefined(e)&&"get"in e&&"function"==typeof e.get}(e)?e:function(){const e=/* @__PURE__ */new Map;return{get:t=>e.get(t)??null,set:(t,n)=>{e.set(t,n)},remove:t=>{e.delete(t)},keys:()=>e.keys()}}(),n=e?.key;function o(){try{return Array.from(t.keys()).reduce((e,t)=>t.startsWith(q)?[...e,t]:e,[])}catch{return[]}}return{get(e){try{const n=t.get(q+e);if(r.isNull(n))return X();const o=JSON.parse(n);return Y(o.data,Temporal.Instant.from(o.at))}catch{return X()}},set(e,n){if(n.data!==V&&!r.isNull(n.at))try{t.set(q+e,JSON.stringify({data:n.data,at:n.at.toString()}))}catch{return}},remove(e){try{t.remove(q+e)}catch{return}},clear(){for(const e of o())try{t.remove(e)}catch{continue}},*keys(){for(const e of o())yield e.slice(3)},scope(e){if(r.isUndefined(n)||r.isNullable(e))return"";try{const t=n({env:e});return r.isNullable(t)?"":t}catch{return""}}}}const re=/* @__PURE__ */new WeakMap,oe=/* @__PURE__ */new Map,se=[];function ce(e,t,n,o){const s=r.isNull(n)?"":`${n}:`,c=(e,n)=>{const r=t.scope(e);return`${""===r?"":`${r}:`}${s}${function(e){return JSON.stringify(e)}(n)}`},i=I(`resource:${e.name||"anonymous"}`,N.Broadcast),a=(e,n)=>{const o=t.get(c(n,e));return o.data===V||r.isNull(o.at)?{data:V,at:null}:{data:o.data,at:o.at}},u=(n,r,o,s)=>e({env:n,controller:r,params:o,dispatch:s}).then(e=>(t.set(c(n,o),Y(e,Temporal.Now.instant())),s(i(o),e),e)),l=e=>{const n=o(),r=t.scope(n),c=""===r?s:`${r}:${s}`,i=Object.entries(e);for(const o of[...t.keys()])if(o.startsWith(c))try{const e=JSON.parse(o.slice(c.length));i.every(([t,n])=>e[t]===n)&&t.remove(o)}catch{continue}};function f(e){return{run:u,read:e=>a(e,o()),evict:l,params:e??{}}}return se.push(l),Object.defineProperty(f,"get",{value:function(e){const{data:t}=a(e??{},o());return t===V?null:t},enumerable:!1}),Object.defineProperty(f,"action",{value:function(e){return i(e??{})},enumerable:!1}),f}function ie(e,t,n){const o=e,s=n??(()=>{});return r.isUndefined(t)?ce(o,function(e){const t=re.get(e);if(r.isNotNullable(t))return t;const n=ne();return re.set(e,n),n}(o),null,s):ce(o,t,function(e){const t=oe.get(e);if(r.isNotNullable(t))return t;const n=String(oe.size);return oe.set(e,n),n}(o),s)}let ae=(e=21)=>{let t="",n=crypto.getRandomValues(new Uint8Array(e|=0));for(;e--;)t+="useandom-26T198340PX75pxJACKVERYMINDBUSHWOLF_GQZbfghjklqvwyzrict"[63&n[e]];return t};var ue=/* @__PURE__ */(e=>(e[e.Add=1]="Add",e[e.Remove=2]="Remove",e[e.Update=4]="Update",e[e.Move=8]="Move",e[e.Replace=16]="Replace",e[e.Sort=32]="Sort",e[e.Create=64]="Create",e[e.Fetch=128]="Fetch",e[e.Clone=256]="Clone",e[e.Archive=512]="Archive",e[e.Restore=1024]="Restore",e[e.Merge=2048]="Merge",e[e.Reorder=4096]="Reorder",e[e.Sync=8192]="Sync",e[e.Publish=16384]="Publish",e[e.Link=32768]="Link",e[e.Unlink=65536]="Unlink",e[e.Lock=131072]="Lock",e[e.Unlock=262144]="Unlock",e[e.Import=524288]="Import",e[e.Export=1048576]="Export",e[e.Transfer=2097152]="Transfer",e))(ue||{}),le=/* @__PURE__ */(e=>(e[e.Produce=0]="Produce",e[e.Hydrate=1]="Hydrate",e))(le||{}),fe=/* @__PURE__ */(e=>(e.Property="property",e.Process="process",e.Value="value",e.Operation="operation",e))(fe||{});class de{[s]=!0;static keys=new Set(Object.values(fe));property=null;process=null;value;operation;constructor(e,t){this.value=e,this.operation=t}assign(e,t){const n=new de(this.value,this.operation);return n.property=e,n.process=t,n}}class he{static immer=(()=>{c();const e=new i;return e.setAutoFreeze(!1),e})();static tag="κ";static id=ae}const pe=/* @__PURE__ */Symbol("Box");function me(e,t){const n="string"==typeof t?""===t?[]:t.split("."):t;let r=e;for(const o of n){if(null==r)return;r=r[o]}return r}function ye(e){if(r.isNullable(e)||ge(e))return e;if(r.isArray(e))return e.map(e=>ye(e));if(r.isObject(e)&&be(e)){const t=Object.entries(e).map(([e,t])=>[e,ye(t)]);return{...Object.fromEntries(t),[he.tag]:e[he.tag]??he.id()}}return e}function ve(e){if(Array.isArray(e))return e.filter(e=>he.tag in e).map(e=>e[he.tag]??"").join(",");const t=e[he.tag];if(t)return t;try{return JSON.stringify(e)}catch{return`[unserializable:${typeof e}]`}}function be(e){const t=Object.getPrototypeOf(e);return t===Object.prototype||null===t}function ge(e){return r.isNullable(e)||r.isString(e)||r.isNumber(e)||r.isBoolean(e)||"symbol"==typeof e||"bigint"==typeof e}function we(e){return r.isObject(e)&&pe in e}function Oe(e,t,n,o,s,c){return function i(a,u=t.path){if(a instanceof de){const t=me(n,u.join("."));if(Object.entries(a).filter(([e,t])=>!de.keys.has(e)&&t instanceof de).forEach(([e,t])=>i(t,u.concat(e))),ge(a.value)){if(e===le.Hydrate)return a.value;const i=u.slice(0,-1),l=i.length>0?me(n,i.join(".")):n;return r.isNullable(l)||Pe(l,a,u.at(-1),o,s,c),t??a.value}if(e===le.Hydrate){const e=ye(i(a.value,u));return Pe(e,a,null,o,s,c),e}const l=t??ye(a.value);return Pe(l,a,null,o,s,c),r.isNullable(t)?l:(i(a.value,u),t)}if(r.isArray(a))return a.map((e,t)=>i(e,u.concat(t)));if(r.isObject(a)&&!be(a))return a;if(r.isObject(a)){const t=Object.entries(a).map(([e,t])=>[e,i(t,u.concat(e))]),n=Object.fromEntries(t);if(e===le.Hydrate){const e=ye(n);return Object.entries(a).forEach(([t,n])=>{n instanceof de&&ge(n.value)&&Pe(e,n,t,o,s,c)}),e}return n}return a}(t.value)}function Pe(e,t,n,r,o,s){const c=s(e),i=o.get(c)??[];o.set(c,[t.assign(n,r),...i])}class je{#e={};#t;#n=/* @__PURE__ */new Map;#r=/* @__PURE__ */new Set;#o=!1;constructor(e=ve){this.#t=e}static pk(){return ae()}static"κ"=je.pk;annotate(e,t){return new de(t,e)}"δ"=this.annotate;get model(){return this.#e}get inspect(){return function(e,t,n,s,c){function i(s){const c=s.at(-1),i=me(e(),s),a=s.slice(0,-1),u=o.isNotEmpty(a)?me(e(),a):e();return[...r.isObject(i)||r.isArray(i)?t.get(n(i))?.filter(e=>r.isNullable(e.property))??[]:[],...r.isObject(u)?t.get(n(u))?.filter(e=>e.property===c)??[]:[]]}return function t(n){return new Proxy(()=>{},{get:(r,a)=>"pending"===a?()=>!o.isEmpty(i(n)):"remaining"===a?()=>o.length(i(n)):"box"===a?()=>({value:me(e(),n),inspect:t(n),[pe]:!0}):"is"===a?e=>i(n).some(t=>0!==(t.operation&e)):"draft"===a?()=>o.head(i(n))?.value??me(e(),n):"settled"===a?()=>new Promise(t=>{if(o.isEmpty(i(n)))return t(me(e(),n));const r=()=>{o.isEmpty(i(n))&&(c(r),t(me(e(),n)))};s(r)}):t([...n,String(a)])})}([])}(()=>this.#e,this.#n,this.#t,e=>this.#r.add(e),e=>this.#r.delete(e))}hydrate(e){return this.#o=!0,this.#s(le.Hydrate,()=>e)}produce(e){if(!this.#o)throw new Error("State must be hydrated using hydrate() before calling produce()");return this.#s(le.Produce,e)}#s(e,t){const n=/* @__PURE__ */Symbol("process"),[,r]=he.immer.produceWithPatches(this.#e,t);return this.#e=r.reduce((t,r)=>he.immer.applyPatches(t,[{...r,value:Oe(e,r,t,n,this.#n,this.#t)}]),this.#e),this.#e=ye(this.#e),this.#c(),n}prune(e){this.#n.forEach((t,n)=>{const r=t.filter(t=>t.process!==e);o.isEmpty(r)?this.#n.delete(n):this.#n.set(n,r)}),this.#c()}#c(){this.#r.forEach(e=>e())}observe(e){const t=()=>e(this.#e);return this.#r.add(t),()=>this.#r.delete(t)}}function Se({action:e,renderer:t}){const o=m(),s=n.useContext(B),c=Q(),i=n.useMemo(()=>{const t=s.get(e);if(t)return t;const n=new je,c=o.getCached(e);r.isNotNullable(c)&&n.hydrate({value:c});const i={state:n,listeners:/* @__PURE__ */new Set};return s.set(e,i),i},[e,o,s]);n.useLayoutEffect(()=>{function t(e){i.state.hydrate({value:e}),i.listeners.forEach(e=>e())}return i.listeners.add(c),o.on(e,t),()=>{i.listeners.delete(c),o.off(e,t)}},[e,o,i]);const a=i.state.model?.value;return r.isNullable(a)?null:t(a,i.state.inspect.value)}function Ee(e,t){const n=t.split(".");let r=e;for(let o=0;o<n.length-1;o++)r=r[n[o]];return{cursor:r,key:n[n.length-1]}}function xe(e,t,n){const{cursor:r,key:o}=Ee(e,t);r[o]=n}function Ce(e){return(t,n)=>{t.actions.produce(t=>{xe(t.model,e,n)})}}function Me(e){return t=>{t.actions.produce(t=>{!function(e,t){const{cursor:n,key:r}=Ee(e,t);n[r]=!n[r]}(t.model,e)})}}function ke(e,t){return n=>{n.actions.produce(n=>{xe(n.model,e,t)})}}function Ne(){const e=n.useRef(null);return n.useMemo(()=>({actions:{dispatch:function(t,n){const r=e.current;if(!r)throw new Error("march-hare: useContext handle dispatched before its paired context.useActions(...) ran. Call context.actions.dispatch from event handlers, not synchronously during render.");return r(t,n)}},useActions:function(...t){const s=function(...e){const t=r.isUndefined(e[0])||r.isFunction(e[0])?{}:e[0],s=r.isFunction(e[0])?e[0]:e[1]??(()=>({})),c=m(),i=n.useContext(te),u=n.useContext(v),l=w(),f=n.useContext(g),h=n.useContext(R),p=n.useContext(L),y=Q(),b=n.useRef(!1),P=n.useRef(null),j=n.useRef(new je);b.current||(b.current=!0,P.current=j.current.hydrate(t));const[S,E]=n.useState(()=>j.current.model),x=function(e){const t=n.useRef(e);return t.current=e,n.useMemo(()=>{return n=t,Object.keys(e).reduce((e,t)=>(Object.defineProperty(e,t,{get:()=>n.current[t],enumerable:!0}),e),{});var n},[e])}(s()),k=n.useMemo(()=>new d,[]),N=n.useRef({handlers:/* @__PURE__ */new Map});N.current.handlers=/* @__PURE__ */new Map;const _=function(){const e=n.useRef(/* @__PURE__ */new Set),t=n.useRef(/* @__PURE__ */new Set);return n.useMemo(()=>({broadcast:e.current,multicast:t.current}),[])}(),U=n.useRef(A.Mounting),W=n.useRef(/* @__PURE__ */new Set),B=n.useRef(0),$=n.useCallback((e,t,n)=>{const o=new AbortController,s={controller:o,action:e,payload:t};return u.add(s),W.current.add(s),{get model(){return j.current.model},get phase(){return U.current},task:s,data:x,tasks:u,env:l,actions:{produce(e){if(o.signal.aborted)return;const t=f.current,r=j.current.produce(t=>{f.current=a(f.current,n=>{e({model:t,inspect:j.current.inspect,env:n})})});E(j.current.model),f.current!==t&&c.emit(M,f.current),n.processes.add(r),P.current&&(n.processes.add(P.current),P.current=null)},dispatch(e,t){if(o.signal.aborted)return Promise.resolve();const n=F(e),r=J(e)?e.channel:void 0;return H(e)?i?G(i.emitter,n,t,r):Promise.resolve():G(z(e)?c:k,n,t,r)},annotate:(e,t=ue.Update)=>j.current.annotate(t,e),get inspect(){return j.current.inspect},resource:Object.assign(function(e){const t=(e,t)=>{const n=e,r=F(n),o=J(n)?n.channel:void 0;return H(n)?i?G(i.emitter,r,t,o):Promise.resolve():z(n)?G(c,r,t,o):Promise.resolve()},n={exceedsWindow:null,isolated:!1},s={then:(s,c)=>(()=>{if(r.isNotNullable(n.exceedsWindow)){const{data:t,at:o}=e.read(e.params);if(t!==V&&r.isNotNullable(o)){const e=Temporal.Now.instant().since(o),r=Temporal.Duration.from(n.exceedsWindow);if(Temporal.Duration.compare(e,r)<=0)return Promise.resolve(t)}}if(n.isolated)return e.run(l,o,e.params,t);let s=h.get(e.run);r.isUndefined(s)&&(s=/* @__PURE__ */new Map,h.set(e.run,s));const c=s,i=JSON.stringify(e.params);let a=c.get(i);if(r.isUndefined(a)){const n=new AbortController,r={controller:n,refs:0};r.promise=e.run(l,n,e.params,t).finally(()=>{c.delete(i)}),c.set(i,r),a=r}const u=a;u.refs+=1;const f=()=>{u.refs-=1,0===u.refs&&(c.delete(i),u.controller.abort(o.signal.reason))};if(o.signal.aborted)f();else{o.signal.addEventListener("abort",f,{once:!0});const e=()=>o.signal.removeEventListener("abort",f);u.promise.then(e,e)}return d=u.promise,p=o.signal,new Promise((e,t)=>{if(p.aborted)return void t(p.reason);const n=()=>t(p.reason);p.addEventListener("abort",n,{once:!0}),d.then(t=>{p.removeEventListener("abort",n),e(t)},e=>{p.removeEventListener("abort",n),t(e)})});var d,p})().then(s,c),exceeds:e=>(n.exceedsWindow=e,s),isolated:()=>(n.isolated=!0,s),evict(t){e.evict(t??e.params)}};return s},{nuke:e=>function(e){const t=e??{};for(const n of se)n(t)}(e)}),async final(e){if(o.signal.aborted)return null;const t=F(e),n=H(e)?i?.emitter??null:c;if(!n)return null;const s=n.getCached(t);if(r.isUndefined(s))return null;const a=j.current.inspect;return a.pending()&&await new Promise((e,t)=>{if(o.signal.aborted)return void t(o.signal.reason);const n=()=>t(o.signal.reason);o.signal.addEventListener("abort",n,{once:!0}),a.settled().then(()=>{o.signal.removeEventListener("abort",n),e()})}),n.getCached(t)??null},peek(e){if(o.signal.aborted)return null;const t=F(e),n=H(e)?i?.emitter??null:c;return n?n.getCached(t)??null:null}}}},[S]);n.useLayoutEffect(()=>{function e(e,t,n){return function(o,s){const a=n();if(r.isNotNullable(s)&&r.isNotNullable(a)&&!function(e,t){for(const n of Object.keys(t))if(e[n]!==t[n])return!1;return!0}(s,a))return;const l={processes:/* @__PURE__ */new Set},d=Promise.withResolvers(),h=$(e,o,l),m=function(e){const t=F(e),n=r.isString(t)?t:t.description??"";return n.startsWith(O())&&n.slice(n.lastIndexOf("/")+1)||"unknown"}(e),v=performance.now(),b=j.current.model,g=f.current;let w,P=!1;function S(){const e=j.current.model,t=f.current;return{model:b===e?null:{before:b,after:e},env:g===t?null:{before:g,after:t}}}function E(){return H(e)?i?G(i.emitter,e,o,s):Promise.resolve():G(z(e)?c:k,e,o,s)}function x(e){P=!0;const t=K(N.current.handlers,"Error"),n=r.isNotNullable(t),s=function(e){return e instanceof Error&&"AbortError"===e.name?Z.Aborted:Z.Errored}(e),i=function(e){return e instanceof Error?e:new Error(String(e))}(e),a={reason:s,error:i,action:m,handled:n,tasks:u,retry:E};c.fire(C,a),n&&t&&k.emit(t,a),p({stage:"end",result:"error",action:{name:m,payload:o},details:{task:h.task,elapsed:performance.now()-v,mutations:S(),error:i,reason:s}})}function M(){for(const e of u)if(e===h.task){u.delete(e),W.current.delete(e);break}l.processes.forEach(e=>j.current.prune(e)),l.processes.size>0&&y(),P||p({stage:"end",result:"success",action:{name:m,payload:o},details:{task:h.task,elapsed:performance.now()-v,mutations:S()}}),d.resolve()}p({stage:"start",action:{name:m,payload:o},details:{task:h.task}});try{w=t(h,o)}catch(A){return x(A),M(),d.promise}return function(e){if(!e||"object"!=typeof e)return!1;const t=Object.prototype.toString.call(e);return"[object Generator]"===t||"[object AsyncGenerator]"===t}(w)?((async()=>{for await(const e of w);})().catch(x).finally(M),d.promise):(Promise.resolve(w).catch(x).finally(M),d.promise)}}B.current++;const t=/* @__PURE__ */new Set;return N.current.handlers.forEach((n,r)=>{for(const{getChannel:o,handler:s}of n){const n=e(r,s,o);if(H(r)){if(i){const e=i.emitter;e.on(r,n),t.add(()=>e.off(r,n))}k.on(r,n),_.multicast.add(r),t.add(()=>k.off(r,n))}else z(r)?(c.on(r,n),k.on(r,n),_.broadcast.add(r),t.add(()=>{c.off(r,n),k.off(r,n)})):(k.on(r,n),t.add(()=>k.off(r,n)))}}),()=>{const e=++B.current,n=new Set(t);queueMicrotask(()=>{if(B.current!==e){for(const e of n)e();return}for(const e of W.current)e.controller.abort(new ee("Component unmounted")),u.delete(e);W.current.clear(),U.current=A.Unmounting;const t=K(N.current.handlers,"Unmount");t&&k.emit(t),U.current=A.Unmounted;for(const e of n)e()})}},[k]),function({unicast:e,broadcast:t,dispatchers:s,scope:c,phase:i,data:a,handlers:u}){const l=n.useRef(null),f=n.useRef(!1);n.useLayoutEffect(()=>{if(i.current===A.Mounted)return;i.current=A.Mounting;const n=K(u,"Mount");n&&e.emit(n),s.broadcast.forEach(n=>{for(const{channel:o,value:s}of t.getCachedAll(n))r.isNullable(s)||e.emit(n,s,o)}),c&&s.multicast.forEach(t=>{for(const{channel:n,value:o}of c.emitter.getCachedAll(t))r.isNullable(o)||e.emit(t,o,n)}),i.current=A.Mounted,f.current=!1},[]),n.useEffect(()=>{if(f.current)return;f.current=!0;const t=K(u,"Paint");t&&e.emit(t)},[]),n.useLayoutEffect(()=>{if(r.isNotNullable(l.current)){const t=function(e,t){return Object.keys(t).reduce((n,r)=>e[r]!==t[r]?{...n,[r]:t[r]}:n,{})}(l.current,a);if(o.isNotEmpty(Object.keys(t))){const n=K(u,"Update");n&&e.emit(n,t)}}l.current=a},[a,e])}({unicast:k,broadcast:c,dispatchers:_,scope:i,phase:U,data:s(),handlers:N.current.handlers});const T=n.useMemo(()=>({dispatch(e,t){const n=F(e),r=J(e)?e.channel:void 0;return H(e)?i?G(i.emitter,n,t,r):Promise.resolve():G(z(e)?c:k,n,t,r)},get inspect(){return j.current.inspect},stream:(e,t)=>n.createElement(Se,{action:F(e),renderer:t})}),[S,k]),D=n.useMemo(()=>[S,T,x],[S,T,x]);return D.useAction=(e,t)=>{!function(e,t,r){const o=n.useRef(r);n.useLayoutEffect(()=>{o.current=r});const s=n.useRef(t);n.useLayoutEffect(()=>{s.current=t});const c=n.useCallback((e,t)=>o.current(e,t),[]),i=n.useCallback(()=>J(s.current)?s.current.channel:void 0,[]),a=F(t),u=e.current.handlers.get(a)??/* @__PURE__ */new Set;0===u.size&&e.current.handlers.set(a,u),u.add({getChannel:i,handler:c})}(N,e,t)},D.dispatch=D[1].dispatch,D}(...t);return e.current=s.dispatch,s},with:{update:e=>Ce(e),invert:e=>Me(e),always:(e,t)=>ke(e,t)}}),[])}function Ae(t,r){return{Boundary:function({children:t}){const r=n.useMemo(()=>({id:/* @__PURE__ */Symbol("march-hare.scope/instance"),emitter:new h}),[]);/* @__PURE__ */
7
+ return e(te.Provider,{value:r,children:t})},useContext:function(){return Ne()},useEnv:function(){return w()},Resource:function(e){return ie(e,t,r)}}}function _e(n){const r={current:void 0};return{Boundary:function({children:o}){/* @__PURE__ */
8
8
  return t($,{env:n?.env,tap:n?.tap,children:[
9
- /* @__PURE__ */e(Re,{holder:r}),o]})},useContext:function(){return Me()},useEnv:function(){return w()},Resource:function(e){return ie(e,n?.cache,()=>r.current)},Scope:()=>Ae(n?.cache,()=>r.current)}}function Re({holder:e}){const t=w();return e.current=t,null}const Ue={Update:e=>Ce(e),Invert:e=>Ne(e),Always:(e,t)=>ke(e,t)},Le=new je;function We(e,t=ue.Update){return Le.annotate(t,e)}function Be(e,t){return new Promise((n,r)=>{if(t?.aborted)return void r(new ee);const o=setTimeout(n,e);t?.addEventListener("abort",()=>{clearTimeout(o),r(new ee)},{once:!0})})}async function $e(e,t,n){if(t?.aborted)throw new ee;for(;;){if(await n())return;await Be(e,t)}}function Te(e){return e?Boolean(e&&"symbol"!=typeof e):/* @__PURE__ */Symbol(`pk.${Date.now()}.${crypto.randomUUID()}`)}const Fe=/* @__PURE__ */Object.freeze(/* @__PURE__ */Object.defineProperty({__proto__:null,pk:Te,poll:$e,sleep:Be,unset:q,"ζ":Be,"κ":Te,"π":$e},Symbol.toStringTag,{value:"Module"})),ze=/* @__PURE__ */Object.freeze(/* @__PURE__ */Object.defineProperty({__proto__:null,Resource:function(e){return ie(e)},Scope:function(){return Ae()},useContext:function(){return Me()},useEnv:function(){return w()}},Symbol.toStringTag,{value:"Module"}));export{ee as Aborted,J as Action,_e as App,$ as Boundary,ne as Cache,M as Distribution,k as Lifecycle,ue as Op,ue as Operation,Z as Reason,je as State,Ue as With,We as annotate,we as isBox,ze as shared,Fe as utils};
9
+ /* @__PURE__ */e(Re,{holder:r}),o]})},useContext:function(){return Ne()},useEnv:function(){return w()},Resource:function(e){return ie(e,n?.cache,()=>r.current)},Scope:()=>Ae(n?.cache,()=>r.current)}}function Re({holder:e}){const t=w();return e.current=t,null}const Ue={Update:e=>Ce(e),Invert:e=>Me(e),Always:(e,t)=>ke(e,t)},Le=new je;function We(e,t=ue.Update){return Le.annotate(t,e)}function Be(e,t){return new Promise((n,r)=>{if(t?.aborted)return void r(new ee);const o=setTimeout(n,e);t?.addEventListener("abort",()=>{clearTimeout(o),r(new ee)},{once:!0})})}async function $e(e,t,n){if(t?.aborted)throw new ee;for(;;){if(await n())return;await Be(e,t)}}function Te(e){return e?Boolean(e&&"symbol"!=typeof e):/* @__PURE__ */Symbol(`pk.${Date.now()}.${crypto.randomUUID()}`)}const Fe=/* @__PURE__ */Object.freeze(/* @__PURE__ */Object.defineProperty({__proto__:null,pk:Te,poll:$e,sleep:Be,unset:V,"ζ":Be,"κ":Te,"π":$e},Symbol.toStringTag,{value:"Module"})),ze=/* @__PURE__ */Object.freeze(/* @__PURE__ */Object.defineProperty({__proto__:null,Resource:function(e){return ie(e)},Scope:function(){return Ae()},useContext:function(){return Ne()},useEnv:function(){return w()}},Symbol.toStringTag,{value:"Module"}));export{ee as Aborted,I as Action,_e as App,$ as Boundary,ne as Cache,N as Distribution,k as Lifecycle,ue as Op,ue as Operation,Z as Reason,je as State,Ue as With,We as annotate,we as isBox,ze as shared,Fe as utils};
10
10
  //# sourceMappingURL=march-hare.js.map