@directive-run/react 0.1.1 → 0.3.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/dist/index.d.ts CHANGED
@@ -1,7 +1,6 @@
1
1
  import * as react_jsx_runtime from 'react/jsx-runtime';
2
- import * as react from 'react';
3
2
  import { ReactNode } from 'react';
4
- import { SingleModuleSystem, DistributableSnapshot, createRequirementStatusPlugin, ModuleSchema, InferFacts, InferDerivations, Plugin, DebugConfig, ErrorBoundaryConfig, ModuleDef, InferEvents, RequirementTypeStatus, InferSelectorState, TimeTravelState } from '@directive-run/core';
3
+ import { DistributableSnapshot, createRequirementStatusPlugin, ModuleSchema, InferFacts, InferDerivations, Plugin, DebugConfig, ErrorBoundaryConfig, ModulesMap, ModuleDef, SingleModuleSystem, InferEvents, NamespacedSystem, RequirementTypeStatus, InferSelectorState, TimeTravelState } from '@directive-run/core';
5
4
  export { RequirementTypeStatus } from '@directive-run/core';
6
5
  import { ConstraintInfo, InspectState } from '@directive-run/core/adapter-utils';
7
6
  export { ConstraintInfo, InspectState, shallowEqual } from '@directive-run/core/adapter-utils';
@@ -27,24 +26,37 @@ declare function useDerived<S extends ModuleSchema, K extends keyof InferDerivat
27
26
  * When a default value is provided, the system parameter may be
28
27
  * null | undefined — the hook returns the default and recomputes
29
28
  * when the system becomes available.
29
+ *
30
+ * An optional equality function can be passed as the 4th parameter
31
+ * to customize when the selector result is considered "changed".
32
+ * Defaults to `Object.is`. Use `shallowEqual` (exported from this
33
+ * package) when your selector returns a new object/array each time.
34
+ *
35
+ * @example
36
+ * ```tsx
37
+ * // Basic usage
38
+ * const count = useSelector(system, (s) => s.count);
39
+ *
40
+ * // With default value (allows nullable system)
41
+ * const count = useSelector(system, (s) => s.count, 0);
42
+ *
43
+ * // With default value + custom equality
44
+ * const coords = useSelector(system, (s) => ({ x: s.x, y: s.y }), { x: 0, y: 0 }, shallowEqual);
45
+ * ```
30
46
  */
31
- declare function useSelector<S extends ModuleSchema, R>(system: SingleModuleSystem<S>, selector: (state: InferSelectorState<S>) => R, equalityFn?: (a: R, b: R) => boolean): R;
47
+ declare function useSelector<S extends ModuleSchema, R>(system: SingleModuleSystem<S>, selector: (state: InferSelectorState<S>) => R): R;
32
48
  declare function useSelector<S extends ModuleSchema, R>(system: SingleModuleSystem<S>, selector: (state: InferSelectorState<S>) => R, defaultValue: R, equalityFn?: (a: R, b: R) => boolean): R;
33
49
  declare function useSelector<S extends ModuleSchema, R>(system: SingleModuleSystem<S> | null | undefined, selector: (state: InferSelectorState<S>) => R, defaultValue: R, equalityFn?: (a: R, b: R) => boolean): R;
34
- declare function useSelector<R>(system: SingleModuleSystem<any>, selector: (state: Record<string, any>) => R, equalityFn?: (a: R, b: R) => boolean): R;
50
+ declare function useSelector<Modules extends ModulesMap, R>(system: NamespacedSystem<Modules>, selector: (state: NamespacedSystem<Modules>) => R): R;
51
+ declare function useSelector<Modules extends ModulesMap, R>(system: NamespacedSystem<Modules>, selector: (state: NamespacedSystem<Modules>) => R, defaultValue: R, equalityFn?: (a: R, b: R) => boolean): R;
52
+ declare function useSelector<Modules extends ModulesMap, R>(system: NamespacedSystem<Modules> | null | undefined, selector: (state: NamespacedSystem<Modules>) => R, defaultValue: R, equalityFn?: (a: R, b: R) => boolean): R;
53
+ declare function useSelector<R>(system: SingleModuleSystem<any>, selector: (state: Record<string, any>) => R, defaultValue?: R, equalityFn?: (a: R, b: R) => boolean): R;
35
54
  declare function useSelector<R>(system: SingleModuleSystem<any> | null | undefined, selector: (state: Record<string, any>) => R, defaultValue: R, equalityFn?: (a: R, b: R) => boolean): R;
36
55
  declare function useDispatch<S extends ModuleSchema>(system: SingleModuleSystem<S>): (event: InferEvents<S>) => void;
37
56
  /** Watch a derivation or fact by key (auto-detected). When a key exists in both facts and derivations, the derivation overload takes priority. */
38
57
  declare function useWatch<S extends ModuleSchema, K extends keyof InferDerivations<S> & string>(system: SingleModuleSystem<S>, key: K, callback: (newValue: InferDerivations<S>[K], prevValue: InferDerivations<S>[K] | undefined) => void): void;
39
58
  /** Watch a fact key with auto-detection. */
40
59
  declare function useWatch<S extends ModuleSchema, K extends keyof InferFacts<S> & string>(system: SingleModuleSystem<S>, key: K, callback: (newValue: InferFacts<S>[K] | undefined, prevValue: InferFacts<S>[K] | undefined) => void): void;
41
- /**
42
- * Watch a fact by explicit "fact" discriminator.
43
- * @deprecated Use `useWatch(system, key, callback)` instead — facts are now auto-detected.
44
- */
45
- declare function useWatch<S extends ModuleSchema, K extends keyof InferFacts<S> & string>(system: SingleModuleSystem<S>, kind: "fact", factKey: K, callback: (newValue: InferFacts<S>[K] | undefined, prevValue: InferFacts<S>[K] | undefined) => void): void;
46
- /** Watch a fact or derivation (generic fallback) */
47
- declare function useWatch<T>(system: SingleModuleSystem<any>, key: string, callback: (newValue: T, prevValue: T | undefined) => void): void;
48
60
  /** Options for useInspect */
49
61
  interface UseInspectOptions {
50
62
  /** Throttle updates to this interval (ms). When set, uses useState instead of useSyncExternalStore. */
@@ -103,6 +115,12 @@ interface DirectiveRefBaseConfig {
103
115
  type UseDirectiveRefOptions<M extends ModuleSchema> = ModuleDef<M> | (DirectiveRefBaseConfig & {
104
116
  module: ModuleDef<M>;
105
117
  });
118
+ /** Options for useDirectiveRef with namespaced modules */
119
+ type UseDirectiveRefNamespacedOptions<Modules extends ModulesMap> = DirectiveRefBaseConfig & {
120
+ modules: {
121
+ [K in keyof Modules]: Modules[K];
122
+ };
123
+ };
106
124
  /** Without status (no config): returns system directly */
107
125
  declare function useDirectiveRef<M extends ModuleSchema>(options: UseDirectiveRefOptions<M>): SingleModuleSystem<M>;
108
126
  /** Without status (with config): returns system directly */
@@ -114,6 +132,26 @@ declare function useDirectiveRef<M extends ModuleSchema>(options: UseDirectiveRe
114
132
  system: SingleModuleSystem<M>;
115
133
  statusPlugin: StatusPlugin;
116
134
  };
135
+ /** Namespaced: returns NamespacedSystem directly */
136
+ declare function useDirectiveRef<const Modules extends ModulesMap>(options: UseDirectiveRefNamespacedOptions<Modules>): NamespacedSystem<Modules>;
137
+ /** Namespaced with config: returns NamespacedSystem directly */
138
+ declare function useDirectiveRef<const Modules extends ModulesMap>(options: UseDirectiveRefNamespacedOptions<Modules>, config: DirectiveRefBaseConfig): NamespacedSystem<Modules>;
139
+ /**
140
+ * React hook to select derived values from a NamespacedSystem.
141
+ * Uses useSyncExternalStore for tear-free reads.
142
+ *
143
+ * @param system - The namespaced system to read from
144
+ * @param keys - Namespaced keys to subscribe to (e.g., ["auth.token", "data.count"])
145
+ * @param selector - Function that reads from system.facts / system.derive
146
+ *
147
+ * @example
148
+ * ```tsx
149
+ * const system = useDirectiveRef({ modules: { auth, data } });
150
+ * const token = useNamespacedSelector(system, ["auth.token"], (s) => s.facts.auth.token);
151
+ * const count = useNamespacedSelector(system, ["data.*"], (s) => s.derive.data.total);
152
+ * ```
153
+ */
154
+ declare function useNamespacedSelector<Modules extends ModulesMap, R>(system: NamespacedSystem<Modules>, keys: string[], selector: (system: NamespacedSystem<Modules>) => R): R;
117
155
  /** Options for useDirective hook */
118
156
  interface UseDirectiveOptions<S extends ModuleSchema, FK extends keyof InferFacts<S> & string = never, DK extends keyof InferDerivations<S> & string = never> extends DirectiveRefBaseConfig {
119
157
  /** Fact keys to subscribe to */
@@ -153,19 +191,6 @@ type UseDirectiveReturnWithStatus<S extends ModuleSchema, FK extends keyof Infer
153
191
  * ```
154
192
  */
155
193
  declare function useDirective<S extends ModuleSchema, FK extends keyof InferFacts<S> & string = never, DK extends keyof InferDerivations<S> & string = never>(moduleOrOptions: UseDirectiveRefOptions<S>, selections?: UseDirectiveOptions<S, FK, DK>): UseDirectiveReturn<S, FK, DK> | UseDirectiveReturnWithStatus<S, FK, DK>;
156
- /** Props for DirectiveDevTools component */
157
- interface DirectiveDevToolsProps {
158
- system: SingleModuleSystem<any>;
159
- /** Position of the panel */
160
- position?: "bottom-right" | "bottom-left" | "top-right" | "top-left";
161
- /** Whether the panel starts open */
162
- defaultOpen?: boolean;
163
- }
164
- /**
165
- * Dev-only floating panel that shows system state.
166
- * Tree-shaken in production builds via `process.env.NODE_ENV` check.
167
- */
168
- declare function DirectiveDevTools({ system, position, defaultOpen, }: DirectiveDevToolsProps): ReturnType<typeof react.createElement> | null;
169
194
  /**
170
195
  * Returns the system's events dispatcher. Provides autocomplete for event names
171
196
  * and avoids needing useCallback wrappers for event dispatch.
@@ -249,4 +274,4 @@ declare function DirectiveHydrator({ snapshot, children }: HydratorProps): react
249
274
  */
250
275
  declare function useHydratedSystem<S extends ModuleSchema>(moduleDef: ModuleDef<S>, config?: DirectiveRefBaseConfig): SingleModuleSystem<S>;
251
276
 
252
- export { DirectiveDevTools, type DirectiveDevToolsProps, DirectiveHydrator, type HydratorProps, type OptimisticUpdateResult, type StatusPlugin, type UseDirectiveOptions, type UseDirectiveRefOptions, type UseDirectiveReturn, type UseDirectiveReturnWithStatus, type UseInspectOptions, useConstraintStatus, useDerived, useDirective, useDirectiveRef, useDispatch, useEvents, useExplain, useFact, useHydratedSystem, useInspect, useOptimisticUpdate, useRequirementStatus, useSelector, useSuspenseRequirement, useTimeTravel, useWatch };
277
+ export { DirectiveHydrator, type HydratorProps, type OptimisticUpdateResult, type StatusPlugin, type UseDirectiveOptions, type UseDirectiveRefNamespacedOptions, type UseDirectiveRefOptions, type UseDirectiveReturn, type UseDirectiveReturnWithStatus, type UseInspectOptions, useConstraintStatus, useDerived, useDirective, useDirectiveRef, useDispatch, useEvents, useExplain, useFact, useHydratedSystem, useInspect, useNamespacedSelector, useOptimisticUpdate, useRequirementStatus, useSelector, useSuspenseRequirement, useTimeTravel, useWatch };
package/dist/index.js CHANGED
@@ -1,2 +1,2 @@
1
- import {createContext,useCallback,useSyncExternalStore,useRef,useMemo,useEffect,useState,useContext}from'react';import {createRequirementStatusPlugin,createSystem}from'@directive-run/core';import {assertSystem,runTrackedSelector,createThrottle,buildTimeTravelState,defaultEquality,depsChanged,computeInspectState}from'@directive-run/core/adapter-utils';export{shallowEqual}from'@directive-run/core/adapter-utils';import {jsx,jsxs}from'react/jsx-runtime';var M=Symbol("directive.uninitialized");function me(e,t){return assertSystem("useFact",e),process.env.NODE_ENV!=="production"&&typeof t=="function"&&console.error("[Directive] useFact() received a function. Did you mean useSelector()? useFact() takes a string key or array of keys, not a selector function."),Array.isArray(t)?oe(e,t):se(e,t)}function se(e,t){process.env.NODE_ENV!=="production"&&(t in e.facts.$store.toObject()||console.warn(`[Directive] useFact("${t}") \u2014 fact not found in store. Check that "${t}" is defined in your module's schema.`));let r=useCallback(s=>e.facts.$store.subscribe([t],s),[e,t]),i=useCallback(()=>e.facts[t],[e,t]);return useSyncExternalStore(r,i,i)}function oe(e,t){let r=useRef(M),i=useCallback(o=>e.facts.$store.subscribe(t,o),[e,...t]),s=useCallback(()=>{let o={};for(let n of t)o[n]=e.facts[n];if(r.current!==M){let n=true;for(let u of t)if(!Object.is(r.current[u],o[u])){n=false;break}if(n)return r.current}return r.current=o,o},[e,...t]);return useSyncExternalStore(i,s,s)}function he(e,t){return assertSystem("useDerived",e),process.env.NODE_ENV!=="production"&&typeof t=="function"&&console.error("[Directive] useDerived() received a function. Did you mean useSelector()? useDerived() takes a string key or array of keys, not a selector function."),Array.isArray(t)?ue(e,t):ie(e,t)}function ie(e,t){process.env.NODE_ENV!=="production"&&(t in e.derive||console.warn(`[Directive] useDerived("${t}") \u2014 derivation not found. Check that "${t}" is defined in your module's derive property.`));let r=useCallback(s=>e.subscribe([t],s),[e,t]),i=useCallback(()=>e.read(t),[e,t]);return useSyncExternalStore(r,i,i)}function ue(e,t){let r=useRef(M),i=useCallback(o=>e.subscribe(t,o),[e,...t]),s=useCallback(()=>{let o={};for(let n of t)o[n]=e.read(n);if(r.current!==M){let n=true;for(let u of t)if(!Object.is(r.current[u],o[u])){n=false;break}if(n)return r.current}return r.current=o,o},[e,...t]);return useSyncExternalStore(i,s,s)}function Re(e,t,r,i){let s,o=false,n;typeof r=="function"&&i===void 0?n=r:(r!==void 0&&(s=r,o=true),n=i??defaultEquality),process.env.NODE_ENV!=="production"&&!e&&!o&&console.error("[Directive] useSelector() received a null/undefined system without a default value. Provide a default value as the 3rd parameter: useSelector(system, selector, defaultValue)");let u=useRef(t),l=useRef(n),S=useRef(s);u.current=t,l.current=n,S.current=s;let c=useRef([]),g=useRef([]),y=useRef(M),D=useRef([]),h=useMemo(()=>e?new Set(Object.keys(e.derive)):new Set,[e]),R=useCallback(()=>e?runTrackedSelector(e,h,u.current):{value:S.current,factKeys:[],deriveKeys:[]},[e,h]),a=useCallback(b=>{if(!e)return ()=>{};let K=()=>{for(let p of D.current)p();D.current=[];let{factKeys:F,deriveKeys:T}=R();c.current=F,g.current=T,F.length>0?D.current.push(e.facts.$store.subscribe(F,()=>{let p=R();depsChanged(c.current,p.factKeys,g.current,p.deriveKeys)&&K(),b();})):T.length===0&&D.current.push(e.facts.$store.subscribeAll(b)),T.length>0&&D.current.push(e.subscribe(T,()=>{let p=R();depsChanged(c.current,p.factKeys,g.current,p.deriveKeys)&&K(),b();}));};return K(),()=>{for(let F of D.current)F();D.current=[];}},[e,R]),x=useCallback(()=>{let b;if(!e)b=S.current;else {let{value:K}=R();b=K===void 0&&o?S.current:K;}return y.current!==M&&l.current(y.current,b)?y.current:(y.current=b,b)},[R,e,o]);return useSyncExternalStore(a,x,x)}function xe(e){return assertSystem("useDispatch",e),useCallback(t=>{e.dispatch(t);},[e])}function De(e,t,r,i){assertSystem("useWatch",e);let s=t==="fact"&&typeof r=="string"&&typeof i=="function",o=s?r:t,n=s?i:r,u=useRef(n);u.current=n,useEffect(()=>e.watch(o,(l,S)=>{u.current(l,S);}),[e,o]);}function L(e,t){assertSystem("useInspect",e);let r=ae(e),i=t?.throttleMs,[s,o]=useState(r),n=useRef(null);return useEffect(()=>{if(!i||i<=0){n.current?.cleanup(),n.current=null;return}return n.current?.cleanup(),n.current=createThrottle((...u)=>{o(u[0]);},i),()=>{n.current?.cleanup(),n.current=null;}},[i]),useEffect(()=>{n.current&&n.current.throttled(r);},[r]),!i||i<=0?r:s}function ce(e){return computeInspectState(e)}function ae(e){let t=useRef(null),r=useRef([]),i=useRef([]),s=useRef(null),o=useCallback(u=>{let l=e.facts.$store.subscribeAll(u),S=e.onSettledChange(u);return ()=>{l(),S();}},[e]),n=useCallback(()=>{let u=ce(e),l=u.unmet.length===r.current.length&&u.unmet.every((g,y)=>g.id===r.current[y]),S=u.inflight.length===i.current.length&&u.inflight.every((g,y)=>g.id===i.current[y]),c=u.isSettled===s.current;return l&&S&&c&&t.current?t.current:(t.current=u,r.current=u.unmet.map(g=>g.id),i.current=u.inflight.map(g=>g.id),s.current=u.isSettled,u)},[e]);return useSyncExternalStore(o,n,n)}function ke(e){assertSystem("useTimeTravel",e);let t=useRef(null),r=useCallback(s=>e.onTimeTravelChange(s),[e]),i=useCallback(()=>{let s=buildTimeTravelState(e);return s?(t.current&&t.current.canUndo===s.canUndo&&t.current.canRedo===s.canRedo&&t.current.currentIndex===s.currentIndex&&t.current.totalSnapshots===s.totalSnapshots&&t.current.isPaused===s.isPaused||(t.current=s),t.current):null},[e]);return useSyncExternalStore(r,i,i)}function Me(e,t){return Array.isArray(t)?de(e,t):le(e,t)}function le(e,t){let r=useRef(M),i=useCallback(o=>e.subscribe(o),[e]),s=useCallback(()=>{let o=e.getStatus(t);if(r.current!==M){let n=r.current;if(n.pending===o.pending&&n.inflight===o.inflight&&n.failed===o.failed&&n.isLoading===o.isLoading&&n.hasError===o.hasError&&n.lastError===o.lastError)return r.current}return r.current=o,o},[e,t]);return useSyncExternalStore(i,s,s)}function de(e,t){let r=useRef(null),i=useRef(""),s=useCallback(n=>e.subscribe(n),[e]),o=useCallback(()=>{let n={},u=[];for(let S of t){let c=e.getStatus(S);n[S]=c,u.push(`${S}:${c.pending}:${c.inflight}:${c.failed}:${c.hasError}:${c.lastError?.message??""}`);}let l=u.join("|");return l!==i.current&&(i.current=l,r.current=n),r.current??n},[e,...t]);return useSyncExternalStore(s,o,o)}var $=new WeakMap;function _(e){let t=$.get(e);return t||(t=new Map,$.set(e,t)),t}function Ie(e,t){return Array.isArray(t)?Se(e,t):fe(e,t)}function fe(e,t){let r=e.getStatus(t);if(r.hasError&&r.lastError)throw r.lastError;if(r.isLoading){let i=_(e),s=i.get(t);throw s||(s=new Promise(o=>{let n=e.subscribe(()=>{e.getStatus(t).isLoading||(i.delete(t),n(),o());});}),i.set(t,s)),s}return r}function Se(e,t){let r={},i=false,s=null;for(let o of t){let n=e.getStatus(o);r[o]=n,n.hasError&&n.lastError&&!s&&(s=n.lastError),n.isLoading&&(i=true);}if(s)throw s;if(i){let o=_(e),n=t.slice().sort().join(","),u=o.get(n);throw u||(u=new Promise(l=>{let S=e.subscribe(()=>{t.every(g=>!e.getStatus(g).isLoading)&&(o.delete(n),S(),l());});}),o.set(n,u)),u}return r}function B(e,t){let r=useRef(null),i=useRef(null),s=t?.status===true;if(!r.current){let o="id"in e&&"schema"in e,n=o?e:e.module,u=o?{}:e,l=t?.plugins??u.plugins??[],S=t?.debug??u.debug,c=t?.errorBoundary??u.errorBoundary,g=t?.tickMs??u.tickMs,y=t?.zeroConfig??u.zeroConfig,D=t?.initialFacts??u.initialFacts,h=[...l];s&&(i.current=createRequirementStatusPlugin(),h=[...h,i.current.plugin]),r.current=createSystem({module:n,plugins:h.length>0?h:void 0,debug:S,errorBoundary:c,tickMs:g,zeroConfig:y,initialFacts:D});}return useEffect(()=>{let o=r.current;return o?.start(),()=>{o?.destroy(),r.current=null,i.current=null;}},[]),s?{system:r.current,statusPlugin:i.current}:r.current}function we(e,t={}){let{facts:r,derived:i,status:s,...o}=t,n=r??[],u=i??[],l=n.length===0&&u.length===0,S=s?B(e,{status:true,...o}):B(e,o),c=s?S.system:S,g=s?S.statusPlugin:void 0,y=useMemo(()=>l?Object.keys(c.derive):[],[c,l]),D=useCallback(p=>{let I=[];return l?(I.push(c.facts.$store.subscribeAll(p)),y.length>0&&I.push(c.subscribe(y,p))):(n.length>0&&I.push(c.facts.$store.subscribe(n,p)),u.length>0&&I.push(c.subscribe(u,p))),()=>{for(let P of I)P();}},[c,l,...n,...u,...y]),h=useRef(M),R=useRef(M),a=useRef(null),x=useCallback(()=>{let p,I,P,N;if(l){p=c.facts.$store.toObject(),P=Object.keys(p),I={};for(let k of y)I[k]=c.read(k);N=y;}else {p={};for(let k of n)p[k]=c.facts[k];P=n,I={};for(let k of u)I[k]=c.read(k);N=u;}let C=h.current!==M;if(C){let k=h.current;if(Object.keys(k).length!==P.length)C=false;else for(let V of P)if(!Object.is(k[V],p[V])){C=false;break}}let q=R.current!==M;if(q){let k=R.current;if(Object.keys(k).length!==N.length)q=false;else for(let V of N)if(!Object.is(k[V],I[V])){q=false;break}}let z=C?h.current:p,H=q?R.current:I;return C||(h.current=p),q||(R.current=I),C&&q&&a.current||(a.current={facts:z,derived:H}),a.current},[c,l,...n,...u,...y]),b=useSyncExternalStore(D,x,x),K=useCallback(p=>c.dispatch(p),[c]),F=pe(c),T={system:c,dispatch:K,events:F,facts:b.facts,derived:b.derived};return s&&g?{...T,statusPlugin:g}:T}function Ke({system:e,position:t="bottom-right",defaultOpen:r=false}){let[i,s]=useState(r),o=useRef(null),{isSettled:n,unmet:u,inflight:l}=L(e);useEffect(()=>{i&&o.current&&o.current.focus();},[i]);let S=useCallback(a=>e.facts.$store.subscribeAll(a),[e]),c=useRef(M),g=useCallback(()=>{let a=e.facts.$store.toObject();if(c.current!==M){let x=Object.keys(c.current),b=Object.keys(a);if(x.length===b.length){let K=true;for(let F of b)if(!Object.is(c.current[F],a[F])){K=false;break}if(K)return c.current}}return c.current=a,a},[e]),y=useSyncExternalStore(S,g,g);if(process.env.NODE_ENV==="production")return null;let D={position:"fixed",zIndex:99999,...t.includes("bottom")?{bottom:12}:{top:12},...t.includes("right")?{right:12}:{left:12}};if(!i)return jsx("button",{type:"button",onClick:()=>s(true),"aria-label":`Open Directive DevTools${n?"":" (system working)"}`,"aria-expanded":false,style:{...D,background:"#1a1a2e",color:"#e0e0e0",border:"1px solid #333",borderRadius:6,padding:"6px 12px",cursor:"pointer",fontFamily:"monospace",fontSize:12},children:n?"Directive":"Directive..."});let h=Object.keys(e.derive),R={};for(let a of h)try{R[a]=e.read(a);}catch{R[a]="<error>";}return jsxs("div",{role:"region","aria-label":"Directive DevTools",tabIndex:-1,onKeyDown:a=>{a.key==="Escape"&&s(false);},style:{...D,background:"#1a1a2e",color:"#e0e0e0",border:"1px solid #333",borderRadius:8,padding:12,fontFamily:"monospace",fontSize:11,maxWidth:380,maxHeight:500,overflow:"auto",boxShadow:"0 4px 20px rgba(0,0,0,0.5)"},children:[jsxs("div",{style:{display:"flex",justifyContent:"space-between",marginBottom:8},children:[jsx("strong",{style:{color:"#7c8aff"},children:"Directive DevTools"}),jsx("button",{ref:o,type:"button",onClick:()=>s(false),"aria-label":"Close DevTools",style:{background:"none",border:"none",color:"#888",cursor:"pointer",fontSize:14},children:"\xD7"})]}),jsx("div",{style:{marginBottom:6},"aria-live":"polite",children:jsx("span",{style:{color:n?"#4ade80":"#fbbf24"},children:n?"Settled":"Working..."})}),jsxs("details",{open:true,children:[jsxs("summary",{style:{cursor:"pointer",color:"#7c8aff",marginBottom:4},children:["Facts (",Object.keys(y).length,")"]}),jsxs("table",{style:{width:"100%",borderCollapse:"collapse",fontSize:11},children:[jsx("thead",{children:jsxs("tr",{children:[jsx("th",{style:{textAlign:"left",padding:"2px 4px",color:"#7c8aff"},children:"Key"}),jsx("th",{style:{textAlign:"left",padding:"2px 4px",color:"#7c8aff"},children:"Value"})]})}),jsx("tbody",{children:Object.entries(y).map(([a,x])=>{let b;try{b=typeof x=="object"?JSON.stringify(x):String(x);}catch{b="<error>";}return jsxs("tr",{style:{borderBottom:"1px solid #2a2a4a"},children:[jsx("td",{style:{padding:"2px 4px",color:"#a0a0c0"},children:a}),jsx("td",{style:{padding:"2px 4px"},children:b})]},a)})})]})]}),h.length>0&&jsxs("details",{children:[jsxs("summary",{style:{cursor:"pointer",color:"#7c8aff",marginBottom:4},children:["Derivations (",h.length,")"]}),jsxs("table",{style:{width:"100%",borderCollapse:"collapse",fontSize:11},children:[jsx("thead",{children:jsxs("tr",{children:[jsx("th",{style:{textAlign:"left",padding:"2px 4px",color:"#7c8aff"},children:"Key"}),jsx("th",{style:{textAlign:"left",padding:"2px 4px",color:"#7c8aff"},children:"Value"})]})}),jsx("tbody",{children:Object.entries(R).map(([a,x])=>jsxs("tr",{style:{borderBottom:"1px solid #2a2a4a"},children:[jsx("td",{style:{padding:"2px 4px",color:"#a0a0c0"},children:a}),jsx("td",{style:{padding:"2px 4px"},children:typeof x=="object"?JSON.stringify(x):String(x)})]},a))})]})]}),l.length>0&&jsxs("details",{open:true,children:[jsxs("summary",{style:{cursor:"pointer",color:"#fbbf24",marginBottom:4},children:["Inflight (",l.length,")"]}),jsx("ul",{style:{margin:0,paddingLeft:16},children:l.map(a=>jsxs("li",{style:{fontSize:11},children:[a.resolverId," (",a.id,")"]},a.id))})]}),u.length>0&&jsxs("details",{open:true,children:[jsxs("summary",{style:{cursor:"pointer",color:"#f87171",marginBottom:4},children:["Unmet (",u.length,")"]}),jsx("ul",{style:{margin:0,paddingLeft:16},children:u.map(a=>jsxs("li",{style:{fontSize:11},children:[a.requirement.type," from ",a.fromConstraint]},a.id))})]})]})}function pe(e){return assertSystem("useEvents",e),useMemo(()=>e.events,[e])}function Fe(e,t){assertSystem("useExplain",e);let r=useCallback(s=>{let o=e.facts.$store.subscribeAll(s),n=e.onSettledChange(s);return ()=>{o(),n();}},[e]),i=useCallback(()=>e.explain(t),[e,t]);return useSyncExternalStore(r,i,i)}function Ee(e,t){assertSystem("useConstraintStatus",e);let r=L(e);return useMemo(()=>{let i=e.inspect();return t?i.constraints.find(s=>s.id===t)??null:i.constraints},[e,t,r])}function Te(e,t,r){assertSystem("useOptimisticUpdate",e);let[i,s]=useState(false),[o,n]=useState(null),u=useRef(null),l=useCallback(()=>{u.current&&(e.restore(u.current),u.current=null),s(false),n(null);},[e]),S=useCallback(c=>{u.current=e.getSnapshot(),s(true),n(null),e.batch(c);},[e]);return useEffect(()=>{if(!(!t||!r||!i))return t.subscribe(()=>{let c=t.getStatus(r);!c.isLoading&&!c.hasError?(u.current=null,s(false)):c.hasError&&(n(c.lastError),l());})},[t,r,i,l]),{mutate:S,isPending:i,error:o,rollback:l}}var W=createContext(null);function Pe({snapshot:e,children:t}){return jsx(W.Provider,{value:e,children:t})}function Ce(e,t){let r=useContext(W),i=useMemo(()=>r?.data?{...t??{},initialFacts:{...t?.initialFacts??{},...r.data}}:t??{},[r,t]);return B(e,i)}export{Ke as DirectiveDevTools,Pe as DirectiveHydrator,Ee as useConstraintStatus,he as useDerived,we as useDirective,B as useDirectiveRef,xe as useDispatch,pe as useEvents,Fe as useExplain,me as useFact,Ce as useHydratedSystem,L as useInspect,Te as useOptimisticUpdate,Me as useRequirementStatus,Re as useSelector,Ie as useSuspenseRequirement,ke as useTimeTravel,De as useWatch};//# sourceMappingURL=index.js.map
1
+ import {createContext,useCallback,useSyncExternalStore,useRef,useMemo,useEffect,useState,useContext}from'react';import {createSystem,createRequirementStatusPlugin}from'@directive-run/core';import {assertSystem,defaultEquality,runTrackedSelector,createThrottle,buildTimeTravelState,depsChanged,computeInspectState}from'@directive-run/core/adapter-utils';export{shallowEqual}from'@directive-run/core/adapter-utils';import {jsx}from'react/jsx-runtime';var h=Symbol("directive.uninitialized");function Re(e,t){return assertSystem("useFact",e),process.env.NODE_ENV!=="production"&&typeof t=="function"&&console.error("[Directive] useFact() received a function. Did you mean useSelector()? useFact() takes a string key or array of keys, not a selector function."),Array.isArray(t)?ne(e,t):te(e,t)}function te(e,t){process.env.NODE_ENV!=="production"&&(t in e.facts.$store.toObject()||console.warn(`[Directive] useFact("${t}") \u2014 fact not found in store. Check that "${t}" is defined in your module's schema.`));let r=useCallback(n=>e.facts.$store.subscribe([t],n),[e,t]),u=useCallback(()=>e.facts[t],[e,t]);return useSyncExternalStore(r,u,u)}function ne(e,t){let r=useRef(h),u=useCallback(o=>e.facts.$store.subscribe(t,o),[e,...t]),n=useCallback(()=>{let o={};for(let s of t)o[s]=e.facts[s];if(r.current!==h){let s=true;for(let i of t)if(!Object.is(r.current[i],o[i])){s=false;break}if(s)return r.current}return r.current=o,o},[e,...t]);return useSyncExternalStore(u,n,n)}function be(e,t){return assertSystem("useDerived",e),process.env.NODE_ENV!=="production"&&typeof t=="function"&&console.error("[Directive] useDerived() received a function. Did you mean useSelector()? useDerived() takes a string key or array of keys, not a selector function."),Array.isArray(t)?se(e,t):re(e,t)}function re(e,t){process.env.NODE_ENV!=="production"&&(t in e.derive||console.warn(`[Directive] useDerived("${t}") \u2014 derivation not found. Check that "${t}" is defined in your module's derive property.`));let r=useCallback(n=>e.subscribe([t],n),[e,t]),u=useCallback(()=>e.read(t),[e,t]);return useSyncExternalStore(r,u,u)}function se(e,t){let r=useRef(h),u=useCallback(o=>e.subscribe(t,o),[e,...t]),n=useCallback(()=>{let o={};for(let s of t)o[s]=e.read(s);if(r.current!==h){let s=true;for(let i of t)if(!Object.is(r.current[i],o[i])){s=false;break}if(s)return r.current}return r.current=o,o},[e,...t]);return useSyncExternalStore(u,n,n)}function he(e,t,r,u){if(e&&e._mode==="namespaced")return ue(e,t,r,u);let n=e,o,s=false,i=u??defaultEquality;r!==void 0&&(o=r,s=true),process.env.NODE_ENV!=="production"&&!n&&!s&&console.error("[Directive] useSelector() received a null/undefined system without a default value. Provide a default value as the 3rd parameter: useSelector(system, selector, defaultValue)");let f=useRef(t),d=useRef(i),c=useRef(o);f.current=t,d.current=i,c.current=o;let g=useRef([]),v=useRef([]),M=useRef(h),y=useRef([]),x=useMemo(()=>n?new Set(Object.keys(n.derive)):new Set,[n]),R=useCallback(()=>n?runTrackedSelector(n,x,f.current):{value:c.current,factKeys:[],deriveKeys:[]},[n,x]),F=useCallback(m=>{if(!n)return ()=>{};let k=()=>{for(let S of y.current)S();y.current=[];let{factKeys:I,deriveKeys:p}=R();g.current=I,v.current=p,I.length>0?y.current.push(n.facts.$store.subscribe(I,()=>{let S=R();depsChanged(g.current,S.factKeys,v.current,S.deriveKeys)&&k(),m();})):p.length===0&&y.current.push(n.facts.$store.subscribeAll(m)),p.length>0&&y.current.push(n.subscribe(p,()=>{let S=R();depsChanged(g.current,S.factKeys,v.current,S.deriveKeys)&&k(),m();}));};return k(),()=>{for(let I of y.current)I();y.current=[];}},[n,R]),N=useCallback(()=>{let m;if(!n)m=c.current;else {let{value:k}=R();m=k===void 0&&s?c.current:k;}return M.current!==h&&d.current(M.current,m)?M.current:(M.current=m,m)},[R,n,s]);return useSyncExternalStore(F,N,N)}function ue(e,t,r,u){let n=r!==void 0,o=u??defaultEquality,s=useRef(t),i=useRef(o),f=useRef(r);s.current=t,i.current=o,f.current=r;let d=useRef(h),c=useMemo(()=>Object.keys(e.facts),[e]),g=useCallback(M=>{let y=c.map(x=>`${x}.*`);return e.subscribe(y,M)},[e,c]),v=useCallback(()=>{let M=s.current(e),y=M===void 0&&n?f.current:M;return d.current!==h&&i.current(d.current,y)?d.current:(d.current=y,y)},[e,n]);return useSyncExternalStore(g,v,v)}function Me(e){return assertSystem("useDispatch",e),useCallback(t=>{e.dispatch(t);},[e])}function De(e,t,r){assertSystem("useWatch",e);let u=useRef(r);u.current=r,useEffect(()=>e.watch(t,(n,o)=>{u.current(n,o);}),[e,t]);}function oe(e,t){assertSystem("useInspect",e);let r=ce(e),u=t?.throttleMs,[n,o]=useState(r),s=useRef(null);return useEffect(()=>{if(!u||u<=0){s.current?.cleanup(),s.current=null;return}return s.current?.cleanup(),s.current=createThrottle((...i)=>{o(i[0]);},u),()=>{s.current?.cleanup(),s.current=null;}},[u]),useEffect(()=>{s.current&&s.current.throttled(r);},[r]),!u||u<=0?r:n}function ie(e){return computeInspectState(e)}function ce(e){let t=useRef(null),r=useRef([]),u=useRef([]),n=useRef(null),o=useCallback(i=>{let f=e.facts.$store.subscribeAll(i),d=e.onSettledChange(i);return ()=>{f(),d();}},[e]),s=useCallback(()=>{let i=ie(e),f=i.unmet.length===r.current.length&&i.unmet.every((g,v)=>g.id===r.current[v]),d=i.inflight.length===u.current.length&&i.inflight.every((g,v)=>g.id===u.current[v]),c=i.isSettled===n.current;return f&&d&&c&&t.current?t.current:(t.current=i,r.current=i.unmet.map(g=>g.id),u.current=i.inflight.map(g=>g.id),n.current=i.isSettled,i)},[e]);return useSyncExternalStore(o,s,s)}function xe(e){assertSystem("useTimeTravel",e);let t=useRef(null),r=useCallback(n=>e.onTimeTravelChange(n),[e]),u=useCallback(()=>{let n=buildTimeTravelState(e);return n?(t.current&&t.current.canUndo===n.canUndo&&t.current.canRedo===n.canRedo&&t.current.currentIndex===n.currentIndex&&t.current.totalSnapshots===n.totalSnapshots&&t.current.isPaused===n.isPaused||(t.current=n),t.current):null},[e]);return useSyncExternalStore(r,u,u)}function ke(e,t){return Array.isArray(t)?le(e,t):ae(e,t)}function ae(e,t){let r=useRef(h),u=useCallback(o=>e.subscribe(o),[e]),n=useCallback(()=>{let o=e.getStatus(t);if(r.current!==h){let s=r.current;if(s.pending===o.pending&&s.inflight===o.inflight&&s.failed===o.failed&&s.isLoading===o.isLoading&&s.hasError===o.hasError&&s.lastError===o.lastError)return r.current}return r.current=o,o},[e,t]);return useSyncExternalStore(u,n,n)}function le(e,t){let r=useRef(null),u=useRef(""),n=useCallback(s=>e.subscribe(s),[e]),o=useCallback(()=>{let s={},i=[];for(let d of t){let c=e.getStatus(d);s[d]=c,i.push(`${d}:${c.pending}:${c.inflight}:${c.failed}:${c.hasError}:${c.lastError?.message??""}`);}let f=i.join("|");return f!==u.current&&(u.current=f,r.current=s),r.current??s},[e,...t]);return useSyncExternalStore(n,o,o)}var _=new WeakMap;function j(e){let t=_.get(e);return t||(t=new Map,_.set(e,t)),t}function Ie(e,t){return Array.isArray(t)?fe(e,t):de(e,t)}function de(e,t){let r=e.getStatus(t);if(r.hasError&&r.lastError)throw r.lastError;if(r.isLoading){let u=j(e),n=u.get(t);throw n||(n=new Promise(o=>{let s=e.subscribe(()=>{e.getStatus(t).isLoading||(u.delete(t),s(),o());});}),u.set(t,n)),n}return r}function fe(e,t){let r={},u=false,n=null;for(let o of t){let s=e.getStatus(o);r[o]=s,s.hasError&&s.lastError&&!n&&(n=s.lastError),s.isLoading&&(u=true);}if(n)throw n;if(u){let o=j(e),s=t.slice().sort().join(","),i=o.get(s);throw i||(i=new Promise(f=>{let d=e.subscribe(()=>{t.every(g=>!e.getStatus(g).isLoading)&&(o.delete(s),d(),f());});}),o.set(s,i)),i}return r}function V(e,t){let r=useRef(null),u=useRef(null),n=useRef(null),o=t?.status===true,s="modules"in e;return r.current||(n.current=()=>{if(s){let{modules:N,...m}=e,k=t?.plugins??m.plugins??[],I=t?.debug??m.debug,p=t?.errorBoundary??m.errorBoundary,S=t?.tickMs??m.tickMs,E=t?.zeroConfig??m.zeroConfig,q=t?.initialFacts??m.initialFacts,w=createSystem({modules:N,plugins:k.length>0?k:void 0,debug:I,errorBoundary:p,tickMs:S,zeroConfig:E,initialFacts:q});return w.initialize(),typeof window<"u"&&w.start(),w}let i="id"in e&&"schema"in e,f=i?e:e.module,d=i?{}:e,c=t?.plugins??d.plugins??[],g=t?.debug??d.debug,v=t?.errorBoundary??d.errorBoundary,M=t?.tickMs??d.tickMs,y=t?.zeroConfig??d.zeroConfig,x=t?.initialFacts??d.initialFacts,R=[...c];o&&(u.current=createRequirementStatusPlugin(),R=[...R,u.current.plugin]);let F=createSystem({module:f,plugins:R.length>0?R:void 0,debug:g,errorBoundary:v,tickMs:M,zeroConfig:y,initialFacts:x});return F.initialize(),typeof window<"u"&&F.start(),F},r.current=n.current()),useEffect(()=>(!r.current&&n.current&&(r.current=n.current()),()=>{r.current?.destroy(),r.current=null,u.current=null;}),[]),o&&!s?{system:r.current,statusPlugin:u.current}:r.current}function we(e,t,r){let u=useRef(t);u.current=t;let n=useRef(r);n.current=r;let o=useCallback(i=>e.subscribe(u.current,i),[e]),s=useCallback(()=>n.current(e),[e]);return useSyncExternalStore(o,s,s)}function Ke(e,t={}){let{facts:r,derived:u,status:n,...o}=t,s=r??[],i=u??[],f=s.length===0&&i.length===0,d=n?V(e,{status:true,...o}):V(e,o),c=n?d.system:d,g=n?d.statusPlugin:void 0,v=useMemo(()=>f?Object.keys(c.derive):[],[c,f]),M=useCallback(p=>{let S=[];return f?(S.push(c.facts.$store.subscribeAll(p)),v.length>0&&S.push(c.subscribe(v,p))):(s.length>0&&S.push(c.facts.$store.subscribe(s,p)),i.length>0&&S.push(c.subscribe(i,p))),()=>{for(let E of S)E();}},[c,f,...s,...i,...v]),y=useRef(h),x=useRef(h),R=useRef(null),F=useCallback(()=>{let p,S,E,q;if(f){p=c.facts.$store.toObject(),E=Object.keys(p),S={};for(let b of v)S[b]=c.read(b);q=v;}else {p={};for(let b of s)p[b]=c.facts[b];E=s,S={};for(let b of i)S[b]=c.read(b);q=i;}let w=y.current!==h;if(w){let b=y.current;if(Object.keys(b).length!==E.length)w=false;else for(let T of E)if(!Object.is(b[T],p[T])){w=false;break}}let C=x.current!==h;if(C){let b=x.current;if(Object.keys(b).length!==q.length)C=false;else for(let T of q)if(!Object.is(b[T],S[T])){C=false;break}}let z=w?y.current:p,W=C?x.current:S;return w||(y.current=p),C||(x.current=S),w&&C&&R.current||(R.current={facts:z,derived:W}),R.current},[c,f,...s,...i,...v]),N=useSyncExternalStore(M,F,F),m=useCallback(p=>c.dispatch(p),[c]),k=Se(c),I={system:c,dispatch:m,events:k,facts:N.facts,derived:N.derived};return n&&g?{...I,statusPlugin:g}:I}function Se(e){return assertSystem("useEvents",e),useMemo(()=>e.events,[e])}function Fe(e,t){assertSystem("useExplain",e);let r=useCallback(n=>{let o=e.facts.$store.subscribeAll(n),s=e.onSettledChange(n);return ()=>{o(),s();}},[e]),u=useCallback(()=>e.explain(t),[e,t]);return useSyncExternalStore(r,u,u)}function Ee(e,t){assertSystem("useConstraintStatus",e);let r=oe(e);return useMemo(()=>{let u=e.inspect();return t?u.constraints.find(n=>n.id===t)??null:u.constraints},[e,t,r])}function Ne(e,t,r){assertSystem("useOptimisticUpdate",e);let[u,n]=useState(false),[o,s]=useState(null),i=useRef(null),f=useCallback(()=>{i.current&&(e.restore(i.current),i.current=null),n(false),s(null);},[e]),d=useCallback(c=>{i.current=e.getSnapshot(),n(true),s(null),e.batch(c);},[e]);return useEffect(()=>{if(!(!t||!r||!u))return t.subscribe(()=>{let c=t.getStatus(r);!c.isLoading&&!c.hasError?(i.current=null,n(false)):c.hasError&&(s(c.lastError),f());})},[t,r,u,f]),{mutate:d,isPending:u,error:o,rollback:f}}var A=createContext(null);function qe({snapshot:e,children:t}){return jsx(A.Provider,{value:e,children:t})}function Ce(e,t){let r=useContext(A),u=useMemo(()=>r?.data?{...t??{},initialFacts:{...t?.initialFacts??{},...r.data}}:t??{},[r,t]);return V(e,u)}export{qe as DirectiveHydrator,Ee as useConstraintStatus,be as useDerived,Ke as useDirective,V as useDirectiveRef,Me as useDispatch,Se as useEvents,Fe as useExplain,Re as useFact,Ce as useHydratedSystem,oe as useInspect,we as useNamespacedSelector,Ne as useOptimisticUpdate,ke as useRequirementStatus,he as useSelector,Ie as useSuspenseRequirement,xe as useTimeTravel,De as useWatch};//# sourceMappingURL=index.js.map
2
2
  //# sourceMappingURL=index.js.map