nanoeffects 0.9.0 → 0.11.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{action-creator-BrZF6hXc.d.ts → action-creator-9e8jesRa.d.ts} +28 -12
- package/dist/actions.d.ts +12 -5
- package/dist/actions.js +1 -1
- package/dist/bus-Cdw5ajKF.js +1 -0
- package/dist/context-CJGW6OWj.js +1 -0
- package/dist/{context-plugin--HkNN1ha.d.ts → context-plugin-Xibukkbj.d.ts} +1 -1
- package/dist/{delay-CIHnOh_L.js → delay-BnBdGPh7.js} +1 -1
- package/dist/dev.d.ts +2 -2
- package/dist/effects.d.ts +2 -2
- package/dist/effects.js +1 -1
- package/dist/index.d.ts +2 -2
- package/dist/index.js +1 -1
- package/dist/lifecycle-key-8iX8RUVD.js +1 -0
- package/dist/match.d.ts +1 -1
- package/dist/match.js +1 -1
- package/dist/{module-DqKegXHt.d.ts → module-BlkU3i6B.d.ts} +3 -3
- package/dist/notrace/{action-creator-DHAEgwuh.d.ts → action-creator-DQTwMBwP.d.ts} +27 -11
- package/dist/notrace/actions.d.ts +12 -5
- package/dist/notrace/actions.js +1 -1
- package/dist/notrace/bus-G2AdGObY.js +1 -0
- package/dist/notrace/{context-plugin-BapQkGwQ.d.ts → context-plugin-DlZCkcX9.d.ts} +1 -1
- package/dist/notrace/effects.d.ts +2 -2
- package/dist/notrace/index.d.ts +2 -2
- package/dist/notrace/index.js +1 -1
- package/dist/notrace/lifecycle-key-8iX8RUVD.js +1 -0
- package/dist/notrace/origin-key-BbWN3gmN.js +1 -0
- package/dist/notrace/origin-key-CxK0SkeG.d.ts +10 -0
- package/dist/notrace/{plugin-Cxadz6uU.d.ts → plugin-DOYHG78z.d.ts} +2 -2
- package/dist/notrace/policies.d.ts +1 -1
- package/dist/notrace/policies.js +1 -1
- package/dist/notrace/redux.d.ts +4 -3
- package/dist/notrace/redux.js +1 -1
- package/dist/observable.d.ts +1 -1
- package/dist/oop.d.ts +13 -7
- package/dist/oop.js +1 -1
- package/dist/origin-key-BbWN3gmN.js +1 -0
- package/dist/origin-key-CxK0SkeG.d.ts +10 -0
- package/dist/{plugin-DkXCvsmB.d.ts → plugin-DHkamZdH.d.ts} +2 -2
- package/dist/policies.d.ts +2 -2
- package/dist/policies.js +1 -1
- package/dist/react.d.ts +15 -8
- package/dist/react.js +1 -1
- package/dist/redux.d.ts +4 -3
- package/dist/redux.js +1 -1
- package/dist/scope.d.ts +2 -2
- package/dist/scope.js +1 -1
- package/dist/signal.d.ts +1 -1
- package/dist/signal.js +1 -1
- package/dist/trace.d.ts +30 -1
- package/dist/trace.js +1 -1
- package/dist/{types-KavbvHix.d.ts → types-ByPzv7tw.d.ts} +2 -2
- package/dist/{with-policy-DBV9dh2F.js → with-policy-CW50Edgk.js} +1 -1
- package/dist/{with-policy-CqUS-VWW.d.ts → with-policy-DpCvSZRk.d.ts} +1 -1
- package/docs/actions.md +10 -3
- package/docs/migrating-from-effector.md +1 -1
- package/docs/oop.md +2 -0
- package/docs/package.md +1 -1
- package/docs/plugins.md +16 -1
- package/docs/scope.md +1 -1
- package/docs/stores.md +5 -1
- package/docs/tracing.md +121 -1
- package/llms-full.txt +158 -10
- package/llms.txt +1 -1
- package/package.json +3 -3
- package/dist/bus-CkTHUAvq.js +0 -1
- package/dist/context-COgyNlrC.js +0 -1
- package/dist/notrace/bus-BmCTo8BG.js +0 -1
- package/dist/onAbort-BgMfspK4.js +0 -1
package/dist/notrace/redux.d.ts
CHANGED
|
@@ -1,11 +1,12 @@
|
|
|
1
|
-
import { R as EventMap, p as Bus } from "./action-creator-
|
|
1
|
+
import { R as EventMap, p as Bus } from "./action-creator-DQTwMBwP.js";
|
|
2
|
+
import { t as OriginOptions } from "./origin-key-CxK0SkeG.js";
|
|
2
3
|
//#region src/store/redux/middleware.d.ts
|
|
3
4
|
/** What Redux passes through a middleware: an action is a plain object with a `type`. */
|
|
4
5
|
type ReduxAction = {
|
|
5
6
|
type: string;
|
|
6
7
|
payload?: unknown;
|
|
7
8
|
};
|
|
8
|
-
type NanoeffectsMiddlewareOptions = {
|
|
9
|
+
type NanoeffectsMiddlewareOptions = OriginOptions & {
|
|
9
10
|
/** Return `false` for the actions that the bus should not get. Default: all of them. */
|
|
10
11
|
filter?: (action: ReduxAction) => boolean;
|
|
11
12
|
/** Receives an error that `emit` throws, so `dispatch` does not. Default: the error is thrown. */
|
|
@@ -21,7 +22,7 @@ type ReduxStoreApi<State = unknown> = {
|
|
|
21
22
|
}) => unknown;
|
|
22
23
|
getState: () => State;
|
|
23
24
|
};
|
|
24
|
-
type EffectsMiddlewareOptions = Pick<NanoeffectsMiddlewareOptions, "filter">;
|
|
25
|
+
type EffectsMiddlewareOptions = Pick<NanoeffectsMiddlewareOptions, "filter" | "traceId" | "traceGroupId">;
|
|
25
26
|
/**
|
|
26
27
|
* Makes the Redux middleware that feeds a bus you already have: the actions of
|
|
27
28
|
* the store reach its handlers, and every task gets `ctx.store`, the `dispatch`
|
package/dist/notrace/redux.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
const
|
|
1
|
+
import{t as e}from"./origin-key-BbWN3gmN.js";const t=e=>typeof e==`object`&&!!e&&`type`in e,n=(n,r={})=>{let i=n.emit,a=t=>{try{let a=Reflect.get(n,e);a?a(t,r):i(t)}catch(e){if(!r.onError)throw e;r.onError(e,t)}};return()=>e=>n=>{let i=e(n);return t(n)&&(r.filter?.(n)??!0)&&a(n),i}},r=(e,t={})=>{let r,i=/* @__PURE__ */ new WeakMap,a=e.addContext;e.addContext=e=>{a?.(e);let t=r;if(!t)return;let{type:n}=e;Object.assign(e,{store:{getState:t.getState,dispatch:e=>{typeof e==`object`&&e&&i.set(e,n);let r=e;return t.dispatch(r)}}})};let o=n(e,{...t.traceId===void 0?{}:{traceId:t.traceId},...t.traceGroupId===void 0?{}:{traceGroupId:t.traceGroupId},filter:e=>i.get(e)!==e.type&&(t.filter?.(e)??!0),onError:(e,{type:t})=>{globalThis.console?.error(`[nanoeffects] handler of "${t}" failed`,e)}});return e=>(r=e,o())};export{r as createEffectsMiddleware};
|
package/dist/observable.d.ts
CHANGED
package/dist/oop.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { B as EventMap, _ as Command, h as Bus, t as ActionCreator } from "./action-creator-
|
|
1
|
+
import { B as EventMap, H as ListenerOptions, _ as Command, h as Bus, t as ActionCreator } from "./action-creator-9e8jesRa.js";
|
|
2
2
|
//#region src/oop/types.d.ts
|
|
3
3
|
type Slots = "ctx" | "commands" | "trace" | "addContext" | "applyScope" | "fitScope" | "app" | "use";
|
|
4
4
|
type AnyFunction = (...args: never[]) => unknown;
|
|
@@ -64,8 +64,10 @@ export declare function WithBus(): <C extends Constructor>(Base: C) => Extended<
|
|
|
64
64
|
* Makes a method of a class from `extendBus` or `@WithBus` a handler of `event`
|
|
65
65
|
* for each instance, with `this` bound to the instance, from the construction
|
|
66
66
|
* until `dispose()`. `wrap` takes the bound handler and returns the one to
|
|
67
|
-
* subscribe, such as `latest`.
|
|
68
|
-
*
|
|
67
|
+
* subscribe, such as `latest`. `{ traceId }`, as the second or the third
|
|
68
|
+
* argument, names the method in the trace (see `tracePlugin`). An event emitted
|
|
69
|
+
* inside the constructor of the base class does not reach it: the
|
|
70
|
+
* subscription is made right after.
|
|
69
71
|
*
|
|
70
72
|
* @example
|
|
71
73
|
* ```ts
|
|
@@ -75,11 +77,15 @@ export declare function WithBus(): <C extends Constructor>(Base: C) => Extended<
|
|
|
75
77
|
* }
|
|
76
78
|
* ```
|
|
77
79
|
*/
|
|
78
|
-
export declare function On<P>(event: EventOf<P>, wrap?: Wrap): MethodDecorator<P>;
|
|
79
|
-
export declare function On(event:
|
|
80
|
+
export declare function On<P>(event: EventOf<P>, wrap?: Wrap, options?: ListenerOptions): MethodDecorator<P>;
|
|
81
|
+
export declare function On<P>(event: EventOf<P>, options: ListenerOptions): MethodDecorator<P>;
|
|
82
|
+
export declare function On(event: string, wrap?: Wrap, options?: ListenerOptions): MethodDecorator<never>;
|
|
83
|
+
export declare function On(event: string, options: ListenerOptions): MethodDecorator<never>;
|
|
80
84
|
/** Like `On`, but the handler runs at most once for an instance. */
|
|
81
|
-
export declare function Once<P>(event: EventOf<P>, wrap?: Wrap): MethodDecorator<P>;
|
|
82
|
-
export declare function Once(event:
|
|
85
|
+
export declare function Once<P>(event: EventOf<P>, wrap?: Wrap, options?: ListenerOptions): MethodDecorator<P>;
|
|
86
|
+
export declare function Once<P>(event: EventOf<P>, options: ListenerOptions): MethodDecorator<P>;
|
|
87
|
+
export declare function Once(event: string, wrap?: Wrap, options?: ListenerOptions): MethodDecorator<never>;
|
|
88
|
+
export declare function Once(event: string, options: ListenerOptions): MethodDecorator<never>;
|
|
83
89
|
//#endregion
|
|
84
90
|
//#region src/oop/extend.d.ts
|
|
85
91
|
/**
|
package/dist/oop.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{r as e}from"./bus-
|
|
1
|
+
import{r as e}from"./bus-Cdw5ajKF.js";const t=/* @__PURE__ */ new WeakMap,n=e=>typeof e==`function`,r=e=>Reflect.ownKeys(e).flatMap(t=>{let r=Reflect.getOwnPropertyDescriptor(e,t)?.value;return n(r)?[{key:t,value:r}]:[]}),i=/* @__PURE__ */ new WeakMap,a=e=>{let n=i.get(e);if(n)return n;let a=/* @__PURE__ */ new Set,o=[];for(let n=e;n&&n!==Object.prototype;n=Reflect.getPrototypeOf(n))for(let{key:e,value:i}of r(n)){if(e===`constructor`||a.has(e))continue;a.add(e);let n=t.get(i);n&&o.push({key:e,method:i,spec:n})}return i.set(e,o),o},o=/* @__PURE__ */ new WeakMap,s=e=>typeof e==`object`&&!!e||typeof e==`function`,c=e=>{let t=o.get(e);if(t)return t;let n=/* @__PURE__ */ new Set;return o.set(e,n),n},l=e=>{if(typeof e==`string`)return e;if(s(e)){let t=Reflect.get(e,`type`);return typeof t==`string`?t:e}return e},u=(e,t,n)=>Reflect.apply(Reflect.get(e,t),e,n),d=(e,t,n,r)=>{let[i,a,...o]=r,s=c(e),l={event:i,handler:a,off:()=>{}},d=u(t,n,[i,n===`once`?(e,t)=>(s.delete(l),typeof a==`function`?Reflect.apply(a,null,[e,t]):void 0):a,...o]),f=typeof d==`function`?()=>d():()=>{};return l.off=f,s.add(l),()=>{s.delete(l),f()}},f=(e,t,n)=>{let[r,i]=n,a=c(e);r===void 0&&a.clear();for(let e of[...a])Object.is(l(e.event),l(r))&&(i===void 0||e.handler===i)&&(a.delete(e),e.off());return u(t,`off`,n)},p=e=>{if(!s(e))return;let t=o.get(e);if(t){o.delete(e);for(let e of t)e.off()}},m=/* @__PURE__ */ new Set([`on`,`once`,`off`,`emit`,`ctx`,`commands`,`trace`,`addContext`,`applyScope`,`fitScope`,`app`,`use`]),h=Reflect.get(Symbol,`dispose`),g=e=>typeof e==`function`,_=(e,t,n,r)=>{n in t||Object.defineProperty(e,n,{configurable:!0,enumerable:!1,...r})},v=/* @__PURE__ */ new WeakMap,y=(e,t)=>{let n=v.get(e);if(n)return n;let r={on:(...n)=>d(e,t,`on`,n),once:(...n)=>d(e,t,`once`,n),off:(...n)=>f(e,t,n)};return v.set(e,r),r},b=(e,t)=>(...n)=>Reflect.apply(Reflect.get(e,t),e,n),x=(e,t)=>{for(let{method:n,spec:r}of a(Reflect.getPrototypeOf(e)??{})){let i=(t,r)=>Reflect.apply(n,e,[t,r]),a=r.wrap?r.wrap(i):i,o=r.once?`once`:`on`;d(e,t,o,[r.event,a,r.options])}},S=(e,t,n)=>{for(let r of[`on`,`once`,`off`])_(e,t,r,{get(){return y(this,n)[r]}});_(e,t,`emit`,{value:b(n,`emit`)});for(let[r,i]of Object.entries(n))typeof i==`function`&&!m.has(r)&&_(e,t,r,{value:b(n,r)});let r=function(){p(this)};_(e,t,`dispose`,{value:r}),h&&_(e,t,h,{value:r}),_(e,t,`bus`,{get:()=>n})},C=(e,t)=>{let n=function(...r){let i=Reflect.construct(t,r,new.target??n);return x(i,e),i};return Object.setPrototypeOf(n,t),n.prototype=Object.create(t.prototype,{constructor:{value:n,writable:!0,configurable:!0}}),Object.defineProperty(n,"name",{value:t.name,configurable:!0}),`bus`in t||Object.defineProperty(n,"bus",{value:e,configurable:!0}),S(n.prototype,t.prototype,e),n};function w(t,n){if(g(t))return C(e(),t);if(!n)throw TypeError(`extendBus: pass the class to extend`);return C(t,n)}function T(e){return t=>e?w(e,t):w(t)}const E=e=>{let[t,n,r]=e;return typeof n==`string`||typeof n==`symbol`?Reflect.get(Object(r),`value`):t},D=(e,n,r,i)=>((...a)=>{let o=E(a);if(typeof o==`function`){let a=typeof n==`function`?n:void 0,s=typeof n==`function`?r:n??r;t.set(o,{event:e,wrap:a,once:i,options:s})}});function O(e,t,n){return D(e,t,n,!1)}function k(e,t,n){return D(e,t,n,!0)}export{O as On,k as Once,T as WithBus,p as disposeBus,w as extendBus};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
const e=Symbol.for(`nanoeffects.origin`);export{e as t};
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
//#region src/core/origin-key.d.ts
|
|
2
|
+
/** What an emitter tells the trace about itself. */
|
|
3
|
+
type OriginOptions = {
|
|
4
|
+
/** Names the subscription that emits; it is the `type` of the root task of the trace. */
|
|
5
|
+
traceId?: string;
|
|
6
|
+
/** Names the flow the emit belongs to; every task below it has it too. */
|
|
7
|
+
traceGroupId?: string;
|
|
8
|
+
};
|
|
9
|
+
//#endregion
|
|
10
|
+
export { OriginOptions as t };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { B as EventMap, N as WithContext, V as Keys, b as Context, d as Effects, h as Bus, l as BoundForm } from "./action-creator-
|
|
2
|
-
import { n as NoClash } from "./context-plugin
|
|
1
|
+
import { B as EventMap, N as WithContext, V as Keys, b as Context, d as Effects, h as Bus, l as BoundForm } from "./action-creator-9e8jesRa.js";
|
|
2
|
+
import { n as NoClash } from "./context-plugin-Xibukkbj.js";
|
|
3
3
|
//#region src/utils/delay.d.ts
|
|
4
4
|
/**
|
|
5
5
|
* Resolves after `ms`, or rejects early if `ctx.signal` aborts. `ms` can be a
|
package/dist/policies.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { B as EventMap,
|
|
2
|
-
import { n as withPolicy, t as PolicyFunction } from "./with-policy-
|
|
1
|
+
import { B as EventMap, G as Task } from "./action-creator-9e8jesRa.js";
|
|
2
|
+
import { n as withPolicy, t as PolicyFunction } from "./with-policy-DpCvSZRk.js";
|
|
3
3
|
//#region src/policies/keyed.d.ts
|
|
4
4
|
/** Options shared by every policy that can keep its state per key. */
|
|
5
5
|
type KeyOption<P> = {
|
package/dist/policies.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{
|
|
1
|
+
import{i as e,o as t,s as n,t as r,u as i}from"./context-CJGW6OWj.js";import{n as a,r as o,t as s}from"./delay-BnBdGPh7.js";import{n as c,t as l}from"./promise-CSLpzwSR.js";import{n as u,t as d}from"./lifecycle-key-8iX8RUVD.js";import{t as f}from"./with-policy-CW50Edgk.js";const p=e=>Reflect.get(e,d),m=e=>{p(e)?.start()},h=(e,n,r)=>(m(e),t(e,n,r)),g=(e,t)=>{n(e,t,`drop`),p(e)?.drop()},_=(e,t)=>{p(e)?.done(t)},v=(e,t,n)=>{let r=p(e);t?r?.cancel(n):r?.drop()},y=e=>(Reflect.set(e,u,!0),e),b=()=>{},x=(e,t)=>{let n=/* @__PURE__ */ new Map;return(r,i)=>{let a=e(r),o=n.get(a);if(!o){let e=t(()=>{n.get(a)===e&&n.delete(a)});o=e,n.set(a,e)}return o(r,i)}},S=(e,t)=>y(e?x(e,t):t(b)),C=(e,t={})=>S(t.key,t=>w(`latest`,(t,n,r)=>(r(),e(t,n)),t)),w=(t,a,o=b)=>{let s=null;return(l,u)=>{if(s?.abort(),u.signal.aborted)return;let{ctx:d,unlink:f}=e(u);s=d;let p=r(d,t),h=!1,g=()=>{d.signal.aborted||(h=!0,m(d),n(d,t,`start`))};i(d,e=>{v(d,h,e),p(h?`cancel`:`drop`)});let _=()=>{f(),s===d&&(s=null,o())},y=e=>{if(!d.signal.aborted)return p(h?`done`:`drop`),e};try{let e=a(l,d,g);return c(e)?Promise.resolve(e).then(y,e=>{if(!d.signal.aborted)throw p(`error`,e),e}).finally(_):(_(),y(e))}catch(e){if(_(),d.signal.aborted)return;throw p(`error`,e),e}}},T=(e,t,n={})=>S(n.key,r=>D(e,t,n,r)),E=(e,t,n,r)=>{let i=r!==b,s=null,c=null;return(l,u)=>{if(u.signal.aborted)return;let d=Date.now(),f=s===null||d-s>=e||d-s<0;return s=d,c!==null&&a(c),c=i?o(r,e):null,n&&f?Promise.resolve(h(u,`debounce`,()=>t(l,u))):(g(u,`debounce`),Promise.resolve(void 0))}},D=(e,t,n,r)=>{let a=n.leading??!1,o=n.trailing??!0;if(!o)return E(e,t,a,r);let c=!1,l=0,u=w(`debounce`,([n,r],a,u)=>{let d=l;return i(a,()=>{l===d&&(c=!1)}),s(a,e).then(()=>{if(c=!1,o&&!r)return u(),t(n,a)})},r);return(e,n)=>{if(n.signal.aborted)return;let r=a&&!c;c=!0,l++;let i=u([e,r],n);return r?Promise.resolve(h(n,`debounce`,()=>t(e,n))):i}},O=(e,t={})=>S(t.key,t=>{let n=null;return(r,a)=>{if(a.signal.aborted)return;if(n){g(a,`leading`);return}let o={};n=o;let s=()=>{c(),n===o&&(n=null,t())},c=i(a,s);try{return l(h(a,`leading`,()=>e(r,a)),s)}catch(e){throw s(),e}}}),k=(e,t={})=>S(t.key,n=>A(e,t,n)),A=(e,t,n)=>{let r=t.concurrency??1,a=t.limit??1/0,o=[],s=0,c=()=>{for(;s<r;){let e=o.shift();if(!e)return;e.start()}};return(l,u)=>new Promise((d,f)=>{if(u.signal.aborted){d(void 0);return}let p=b,m=()=>{p(),g(u,`queue`),d(void 0)},v=()=>{if(p(),u.signal.aborted){m();return}s++;let t=!0,r=()=>{t&&(t=!1,s--,c(),s===0&&o.length===0&&n())},a=i(u,()=>{r(),d(void 0)}),g;try{g=Promise.resolve(h(u,`queue`,()=>e(l,u)))}catch(e){g=Promise.reject(e)}let v=()=>{a(),r()};g.then(e=>{_(u,{value:e}),v(),d(u.signal.aborted?void 0:e)},e=>{_(u,{error:e}),v(),u.signal.aborted?d(void 0):f(e)})};if(s<r){v();return}if(o.length>=a){if(t.overflow!==`drop-old`||a<=0){m();return}o.shift()?.drop()}let y={start:v,drop:m};o.push(y),p=i(u,()=>{let e=o.indexOf(y);e>=0&&o.splice(e,1),m()})})},j=(e,t,n={})=>S(n.key,r=>M(e,t,n,r)),M=(e,t,n,r)=>{let i=n.leading??!0,s=n.trailing??!0,c=r!==b,l=null,u=0,d=null,f=null,p=null,m=!1,_=t=>l===null||t-l>=e||t-l<0||t-u>=e,v=e=>g(e,`throttle`),y=()=>{let e=p;p=null,e&&(v(e.ctx),e.resolve())},x=(e,t)=>(y(),new Promise((n,r)=>{p={payload:e,ctx:t,resolve:n,reject:r}})),S=(e,n,r)=>{y(),u=r,m=!0;try{return h(n,`throttle`,()=>t(e,n))}finally{m=!1}},C=()=>{c&&(f=o(w,e))},w=()=>{if(f=null,!c||d!==null||p)return;let t=Date.now(),n=Math.max(e-(t-(l??-1/0)),e-(t-u));n<=0?r():f=o(w,n)},T=e=>{d=null;let t=p;if(s&&t&&!t.ctx.signal.aborted){p=null;try{t.resolve(S(t.payload,t.ctx,e))}catch(e){t.reject(e)}}else y();w()},E=()=>{let t=Date.now();_(t)?T(t):d=o(E,Math.min(e-(t-(l??t)),e-(t-u)))},D=()=>{f!==null&&(a(f),f=null)},O=(e,t)=>{if(!s)v(t);else return x(e,t)},k=(e,t,n,r)=>{if(!r)v(t);else if(u=n,C(),!i)v(t);else return S(e,t,n)},A=(t,n,r,s)=>s&&d!==null?(a(d),d=o(E,e),S(t,n,r)):d===null&&(d=o(E,e),s&&(u=r,i))?S(t,n,r):O(t,n);return(e,t)=>{if(t.signal.aborted)return;let n=Date.now(),r=!m&&_(n);return l=n,D(),s?A(e,t,n,r):k(e,t,n,r)}};export{T as debounce,C as latest,O as leading,k as queue,j as throttle,f as withPolicy};
|
package/dist/react.d.ts
CHANGED
|
@@ -1,9 +1,15 @@
|
|
|
1
|
-
import { B as EventMap,
|
|
2
|
-
import { t as
|
|
1
|
+
import { B as EventMap, G as Task, T as EventKey, h as Bus, r as FreeActionCreator, t as ActionCreator } from "./action-creator-9e8jesRa.js";
|
|
2
|
+
import { t as OriginOptions } from "./origin-key-CxK0SkeG.js";
|
|
3
|
+
import { t as PolicyFunction } from "./with-policy-DpCvSZRk.js";
|
|
3
4
|
//#region src/react/plugin.d.ts
|
|
4
|
-
/** What `reactPlugin` adds to the bus. */
|
|
5
5
|
/** Tells whether two values are the same: `Object.is` unless the caller gives another. */
|
|
6
6
|
type Equals<V> = (previous: V, next: V) => boolean;
|
|
7
|
+
/** The third argument of `useEmitter`. */
|
|
8
|
+
type UseEmitterOptions<V> = OriginOptions & {
|
|
9
|
+
/** Tells whether a new value is the same as the previous one; `Object.is` when absent. */
|
|
10
|
+
equals?: Equals<V>;
|
|
11
|
+
};
|
|
12
|
+
/** What `reactPlugin` adds to the bus. */
|
|
7
13
|
type ReactApi<E extends EventMap> = {
|
|
8
14
|
/**
|
|
9
15
|
* A React hook: after a render commits with a `value` that differs from the
|
|
@@ -13,18 +19,19 @@ type ReactApi<E extends EventMap> = {
|
|
|
13
19
|
* `export const { useEmitter } = bus` gives a free hook.
|
|
14
20
|
*/
|
|
15
21
|
useEmitter: {
|
|
16
|
-
<K extends EventKey<E>>(event: K, value: E[K],
|
|
22
|
+
<K extends EventKey<E>>(event: K, value: E[K], options?: UseEmitterOptions<E[K]>): void;
|
|
17
23
|
/** A creator without a payload type: the payload comes from the event map. */
|
|
18
|
-
<K extends EventKey<E>>(creator: FreeActionCreator<K>, value: E[K],
|
|
19
|
-
<P, T extends string>(creator: ActionCreator<P, T>, value: P,
|
|
24
|
+
<K extends EventKey<E>>(creator: FreeActionCreator<K>, value: E[K], options?: UseEmitterOptions<E[K]>): void;
|
|
25
|
+
<P, T extends string>(creator: ActionCreator<P, T>, value: P, options?: UseEmitterOptions<P>): void;
|
|
20
26
|
};
|
|
21
27
|
};
|
|
22
28
|
/**
|
|
23
29
|
* Adds `bus.useEmitter(event, value)`: a hook that tells the bus when a value of
|
|
24
30
|
* a component changes, without the traps of `useEffect(() => emit(value), [value])`
|
|
25
31
|
* (an emit on mount, two on mount under StrictMode, a new `emit` re-running it).
|
|
26
|
-
* Pass `equals` as the third argument for values that `Object.is` tells apart
|
|
27
|
-
* although they are the same, such as a new object with the same fields.
|
|
32
|
+
* Pass `{ equals }` as the third argument for values that `Object.is` tells apart
|
|
33
|
+
* although they are the same, such as a new object with the same fields. `{ traceId }`
|
|
34
|
+
* names the subscription and `{ traceGroupId }` the flow in the trace of the bus.
|
|
28
35
|
* Needs `react` 18 or newer. Returns the same bus.
|
|
29
36
|
*
|
|
30
37
|
* @example
|
package/dist/react.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{t as e}from"./with-policy-
|
|
1
|
+
import{t as e}from"./with-policy-CW50Edgk.js";import{t}from"./origin-key-BbWN3gmN.js";import{useEffect as n,useMemo as r,useRef as i}from"react";const a=()=>e=>{function r(r,a,o){let s=i(a),c=i({event:r,options:o});n(()=>{c.current={event:r,options:o}}),n(()=>{let{event:n,options:r}=c.current,i=r?.equals??Object.is,o=s.current;if(i(o,a))return;s.current=a;let l=typeof n==`function`?n(a):{type:n,payload:a},u=Reflect.get(e,t);u?u(l,r??{}):e.emit(l)},[a])}return Object.assign(e,{useEmitter:r})},o=(t,a,o=[])=>{let s=i(t);n(()=>{s.current=t});let c=r(()=>e(a((e,t)=>s.current(e,t))),o);return n(()=>()=>c.cancel(),[c]),c};export{a as reactPlugin,o as usePolicy};
|
package/dist/redux.d.ts
CHANGED
|
@@ -1,11 +1,12 @@
|
|
|
1
|
-
import { B as EventMap, h as Bus } from "./action-creator-
|
|
1
|
+
import { B as EventMap, h as Bus } from "./action-creator-9e8jesRa.js";
|
|
2
|
+
import { t as OriginOptions } from "./origin-key-CxK0SkeG.js";
|
|
2
3
|
//#region src/store/redux/middleware.d.ts
|
|
3
4
|
/** What Redux passes through a middleware: an action is a plain object with a `type`. */
|
|
4
5
|
type ReduxAction = {
|
|
5
6
|
type: string;
|
|
6
7
|
payload?: unknown;
|
|
7
8
|
};
|
|
8
|
-
type NanoeffectsMiddlewareOptions = {
|
|
9
|
+
type NanoeffectsMiddlewareOptions = OriginOptions & {
|
|
9
10
|
/** Return `false` for the actions that the bus should not get. Default: all of them. */
|
|
10
11
|
filter?: (action: ReduxAction) => boolean;
|
|
11
12
|
/** Receives an error that `emit` throws, so `dispatch` does not. Default: the error is thrown. */
|
|
@@ -21,7 +22,7 @@ type ReduxStoreApi<State = unknown> = {
|
|
|
21
22
|
}) => unknown;
|
|
22
23
|
getState: () => State;
|
|
23
24
|
};
|
|
24
|
-
type EffectsMiddlewareOptions = Pick<NanoeffectsMiddlewareOptions, "filter">;
|
|
25
|
+
type EffectsMiddlewareOptions = Pick<NanoeffectsMiddlewareOptions, "filter" | "traceId" | "traceGroupId">;
|
|
25
26
|
/**
|
|
26
27
|
* Makes the Redux middleware that feeds a bus you already have: the actions of
|
|
27
28
|
* the store reach its handlers, and every task gets `ctx.store`, the `dispatch`
|
package/dist/redux.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
const
|
|
1
|
+
import{t as e}from"./origin-key-BbWN3gmN.js";const t=e=>typeof e==`object`&&!!e&&`type`in e,n=(n,r={})=>{let i=n.emit,a=t=>{try{let a=Reflect.get(n,e);a?a(t,r):i(t)}catch(e){if(!r.onError)throw e;r.onError(e,t)}};return()=>e=>n=>{let i=e(n);return t(n)&&(r.filter?.(n)??!0)&&a(n),i}},r=(e,t={})=>{let r,i=/* @__PURE__ */ new WeakMap,a=e.addContext;e.addContext=e=>{a?.(e);let t=r;if(!t)return;let{type:n}=e;Object.assign(e,{store:{getState:t.getState,dispatch:e=>{typeof e==`object`&&e&&i.set(e,n);let r=e;return t.dispatch(r)}}})};let o=n(e,{...t.traceId===void 0?{}:{traceId:t.traceId},...t.traceGroupId===void 0?{}:{traceGroupId:t.traceGroupId},filter:e=>i.get(e)!==e.type&&(t.filter?.(e)??!0),onError:(e,{type:t})=>{globalThis.console?.error(`[nanoeffects] handler of "${t}" failed`,e)}});return e=>(r=e,o())};export{r as createEffectsMiddleware};
|
package/dist/scope.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { B as EventMap, a as EmitScope, d as Effects, f as Signaled, h as Bus, o as Scope, u as Effect } from "./action-creator-
|
|
2
|
-
import { n as ScopeSlots, r as Scoped } from "./types-
|
|
1
|
+
import { B as EventMap, a as EmitScope, d as Effects, f as Signaled, h as Bus, o as Scope, u as Effect } from "./action-creator-9e8jesRa.js";
|
|
2
|
+
import { n as ScopeSlots, r as Scoped } from "./types-ByPzv7tw.js";
|
|
3
3
|
//#region src/scope/effect.d.ts
|
|
4
4
|
/**
|
|
5
5
|
* Marks a function whose first parameter is `{ signal }` as an effect, so that
|
package/dist/scope.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{t as e}from"./scope-key-B7l7mUS5.js";const t=/* @__PURE__ */ new WeakSet;function n(e){return t.add(e),e}const r=/* @__PURE__ */ new Set([`signal`,`abort`,`emit`,`on`,`off`,`run`,`type`,`payload`]),i=[],a=Symbol(`nanoeffects.scope.call`),o=Symbol(`nanoeffects.scope.module`),s=Symbol(`nanoeffects.scope.watched`),c=e=>e,l=e=>typeof e==`function`&&t.has(e),u=(e,t)=>(...n)=>Reflect.apply(t,null,[e,...n]),d=(e,t)=>{if(!t)return;for(let n in t)if(n!==`$effects`&&!r.has(n)){let r=t[n];e[n]=l(r)?u(e,r):r}let n=t.$effects;if(n)for(let t in n){let i=n[t];i&&!r.has(t)&&(e[t]=u(e,i))}},f=(e,t,n)=>{d(e,n);for(let n of t)d(e,n)},p=e=>typeof e==`object`&&!!e,m=e=>p(e),h=e=>(p(e)||typeof e==`function`)&&`type`in e,g=e=>h(e)?e.type:e,_=(e,t)=>p(e)&&h(e)?e.payload:t[0],v=t=>p(t)||typeof t==`function`?Reflect.get(t,e):void 0,y=(e,t)=>{let n=v(e),r=p(e)&&m(t[0])?t[0]:void 0;if(n&&r)return[n,r];let i=n??r;return i?[i]:void 0},b=()=>e=>{let t,n,r,l=e=>{let n=e.run;if(n[s])return;let r=(r,...i)=>{let s=t;t=void 0;try{return n((t,n)=>{let i=e[a];return i&&u(n,i,e[o]),r(t,n)},...i)}finally{t=s}};r[s]=!0,e.run=r},u=(e,t,n)=>{e[a]=t,n&&(e[o]=n),f(e,t,n),l(e)},d=e.addContext;e.addContext=e=>{d?.(e);let i=c(e);t&&i.type===n&&Object.is(i.payload,r)&&u(i,t,void 0)},e.applyScope=(e,t)=>{let n=c(e);u(n,n[a]??i,t)},e.fitScope=(t,n)=>typeof n==`function`?(r,i)=>(e.applyScope?.(i,t),Reflect.apply(n,null,[r,i])):n;let p=e.emit;return e.emit=(e,...i)=>{let a=y(e,i);if(!(a||t))return p(e,...i);let o=t,s=n,c=r;t=a,n=g(e),r=_(e,i);try{return p(e,...i)}finally{t=o,n=s,r=c}},e};export{n as effect,b as scopePlugin};
|
|
1
|
+
import{t as e}from"./scope-key-B7l7mUS5.js";const t=/* @__PURE__ */ new WeakSet;function n(e){return t.add(e),e}const r=/* @__PURE__ */ new Set([`signal`,`abort`,`emit`,`on`,`off`,`run`,`type`,`payload`,`traceGroupId`]),i=[],a=Symbol(`nanoeffects.scope.call`),o=Symbol(`nanoeffects.scope.module`),s=Symbol(`nanoeffects.scope.watched`),c=e=>e,l=e=>typeof e==`function`&&t.has(e),u=(e,t)=>(...n)=>Reflect.apply(t,null,[e,...n]),d=(e,t)=>{if(!t)return;for(let n in t)if(n!==`$effects`&&!r.has(n)){let r=t[n];e[n]=l(r)?u(e,r):r}let n=t.$effects;if(n)for(let t in n){let i=n[t];i&&!r.has(t)&&(e[t]=u(e,i))}},f=(e,t,n)=>{d(e,n);for(let n of t)d(e,n)},p=e=>typeof e==`object`&&!!e,m=e=>p(e),h=e=>(p(e)||typeof e==`function`)&&`type`in e,g=e=>h(e)?e.type:e,_=(e,t)=>p(e)&&h(e)?e.payload:t[0],v=t=>p(t)||typeof t==`function`?Reflect.get(t,e):void 0,y=(e,t)=>{let n=v(e),r=p(e)&&m(t[0])?t[0]:void 0;if(n&&r)return[n,r];let i=n??r;return i?[i]:void 0},b=()=>e=>{let t,n,r,l=e=>{let n=e.run;if(n[s])return;let r=(r,...i)=>{let s=t;t=void 0;try{return n((t,n)=>{let i=e[a];return i&&u(n,i,e[o]),r(t,n)},...i)}finally{t=s}};r[s]=!0,e.run=r},u=(e,t,n)=>{e[a]=t,n&&(e[o]=n),f(e,t,n),l(e)},d=e.addContext;e.addContext=e=>{d?.(e);let i=c(e);t&&i.type===n&&Object.is(i.payload,r)&&u(i,t,void 0)},e.applyScope=(e,t)=>{let n=c(e);u(n,n[a]??i,t)},e.fitScope=(t,n)=>typeof n==`function`?(r,i)=>(e.applyScope?.(i,t),Reflect.apply(n,null,[r,i])):n;let p=e.emit;return e.emit=(e,...i)=>{let a=y(e,i);if(!(a||t))return p(e,...i);let o=t,s=n,c=r;t=a,n=g(e),r=_(e,i);try{return p(e,...i)}finally{t=o,n=s,r=c}},e};export{n as effect,b as scopePlugin};
|
package/dist/signal.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { B as EventMap, C as Emit, E as EventLike, a as EmitScope, c as WithScope, h as Bus, v as CommandCall } from "./action-creator-
|
|
1
|
+
import { B as EventMap, C as Emit, E as EventLike, a as EmitScope, c as WithScope, h as Bus, v as CommandCall } from "./action-creator-9e8jesRa.js";
|
|
2
2
|
//#region src/signal/plugin.d.ts
|
|
3
3
|
/** What the second argument of `emit` takes besides the fields of a scope. */
|
|
4
4
|
type SignalOption = {
|
package/dist/signal.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{
|
|
1
|
+
import{u as e}from"./context-CJGW6OWj.js";import{n as t}from"./promise-CSLpzwSR.js";import{n}from"./bus-Cdw5ajKF.js";const r=e=>typeof e==`object`&&!!e,i=(e,t)=>{let n=t[0];if(!r(n)||!r(e)&&typeof e!=`function`)return;let i=Reflect.get(n,`signal`);return i instanceof AbortSignal?i:void 0},a=(r,i,a,o)=>{let s=e({signal:r},e=>{for(let{target:t}of i)t.abort(e)});return t(o)?o.then(s,s):n(a)&&s(),o},o=()=>e=>{let t,n,r=e.addContext;e.addContext=e=>{r?.(e),t?.push({target:e}),n?.aborted&&e.abort(n.reason)};let o=e.emit;return e.emit=(e,...r)=>{let s=i(e,r);if(!(s||t))return o(e,...r);let c=t,l=n,u=[];t=s?u:void 0,n=s;let d;try{d=o(e,...r)}finally{t=c,n=l}return s?a(s,u,e,d):d},e};export{o as signalPlugin};
|
package/dist/trace.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { B as EventMap, J as TraceLogger, K as Trace, L as Tracer, h as Bus, q as TraceEvent } from "./action-creator-9e8jesRa.js";
|
|
2
2
|
//#region src/trace/console.d.ts
|
|
3
3
|
type ConsoleLoggerOptions = {
|
|
4
4
|
/** Defaults to `globalThis.console`. */
|
|
@@ -48,6 +48,34 @@ type PerformanceLoggerOptions = {
|
|
|
48
48
|
*/
|
|
49
49
|
export declare const performanceLogger: (options?: PerformanceLoggerOptions) => TraceLogger;
|
|
50
50
|
//#endregion
|
|
51
|
+
//#region src/trace/plugin.d.ts
|
|
52
|
+
/**
|
|
53
|
+
* Names and groups what the trace shows, on a bus that has a tracer:
|
|
54
|
+
*
|
|
55
|
+
* - `traceGroupId` in the scope of a command, a job or an action goes to every
|
|
56
|
+
* task that the call starts;
|
|
57
|
+
* - `useEmitter` and `bus.emitter` emit from a root task named by their
|
|
58
|
+
* `traceId`, so a chain says which subscription began it;
|
|
59
|
+
* - `bus.on(event, handler, { traceId })` and `once` name a listener: each call of
|
|
60
|
+
* it is a task with that `traceId`, and what it emits is below it.
|
|
61
|
+
*
|
|
62
|
+
* The plugin does nothing on a bus without a tracer, and without it all of these
|
|
63
|
+
* options are ignored, so a project can leave it out, or use it only in
|
|
64
|
+
* development, and nothing else changes. Returns the same bus.
|
|
65
|
+
*
|
|
66
|
+
* @example
|
|
67
|
+
* ```ts
|
|
68
|
+
* import { createBus } from "nanoeffects";
|
|
69
|
+
* import { consoleLogger, createTracer, tracePlugin } from "nanoeffects/trace";
|
|
70
|
+
*
|
|
71
|
+
* const bus = createBus({ trace: createTracer(consoleLogger()) }).use(tracePlugin());
|
|
72
|
+
*
|
|
73
|
+
* // a listener that you can find in the log
|
|
74
|
+
* bus.on("name/changed", saveName, { traceId: "saveNotifier" });
|
|
75
|
+
* ```
|
|
76
|
+
*/
|
|
77
|
+
export declare const tracePlugin: () => <E extends EventMap>(bus: Bus<E>) => Bus<E>;
|
|
78
|
+
//#endregion
|
|
51
79
|
//#region src/trace/recorder.d.ts
|
|
52
80
|
type Recorder<E = Record<string, unknown>> = TraceLogger<E> & {
|
|
53
81
|
/** Every event received so far, in order. */
|
|
@@ -105,6 +133,7 @@ type ReduxDevtoolsState = {
|
|
|
105
133
|
running: Record<number, {
|
|
106
134
|
type: string;
|
|
107
135
|
effect: string;
|
|
136
|
+
traceGroupId?: string;
|
|
108
137
|
}>;
|
|
109
138
|
};
|
|
110
139
|
/**
|
package/dist/trace.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{
|
|
1
|
+
import{a as e,c as t,d as n,n as r,o as i,s as a,u as o}from"./context-CJGW6OWj.js";import{n as s}from"./promise-CSLpzwSR.js";import{t as c}from"./origin-key-BbWN3gmN.js";import{t as l}from"./scope-key-B7l7mUS5.js";const u=(e={})=>{let t=e.console??globalThis.console,n=e.prefix??`[nanoeffects]`,r=/* @__PURE__ */ new Map;return({id:e,parentId:i,type:a,effect:o,phase:s,payload:c,error:l,traceGroupId:u})=>{r.has(e)||r.set(e,typeof i==`number`?(r.get(i)??0)+1:0);let d=` `.repeat(r.get(e)??0);s!==`start`&&r.delete(e);let f=u===void 0?``:` [${u}]`,p=`${n}${f} ${d}${a} · ${o} ${s}`;s===`error`?t?.error(p,l):t?.debug(p,c)}},d=(e={})=>{let t=e.performance??globalThis.performance,n=/* @__PURE__ */ new Map;return({id:e,parentId:r,rootId:i,traceGroupId:a,type:o,effect:s,phase:c,error:l})=>{if(!t)return;if(c===`start`){n.set(e,t.now());return}let u=`${o} · ${s} (${c})`,d={id:e,parentId:r,...i!==void 0&&{rootId:i},...a!==void 0&&{traceGroupId:a},phase:c,...c===`error`&&{error:String(l)}},f=n.get(e);n.delete(e),typeof f==`number`?t.measure(u,{start:f,end:t.now(),detail:d}):t.mark(u,{detail:d})}};let f;const p=()=>f,m=(e,t)=>{let n=f;f=e;try{return t()}finally{f=n}},h=(e,t,n={})=>{let{trace:i}=e;if(!i){e.emit(t);return}let{traceId:o,traceGroupId:s}=n,{ctx:c,unlink:l}=r({event:{type:o??t.type,payload:t,...s===void 0?{}:{traceGroupId:s}},bus:{emit:e.emit,on:e.on,off:e.off,ctx:e.ctx,addContext:e.addContext},tracer:i});a(c,`run`,`start`);try{c.emit(t),a(c,`run`,`done`)}catch(e){throw a(c,`run`,`error`,e),e}finally{l()}},g=e=>typeof e==`string`?e:Reflect.get(Object(e),`type`),_=()=>n=>{if(!(t&&n.trace))return n;let r=n.emit;n.emit=(e,...t)=>m(e,()=>r(e,...t)),Reflect.set(n,c,(e,t)=>{h(n,e,t)});let a=/* @__PURE__ */ new WeakMap,o=(e,t,n)=>{let r=a.get(t)??/* @__PURE__ */ new Map,i=g(e);r.set(i,[...r.get(i)??[],n]),a.set(t,r)},s=(e,t)=>(a.get(t)?.get(g(e)))?.pop(),l=(t,n)=>(r,a)=>(e(a,n),i(a,`run`,()=>t(r,a))),u=(e,t)=>(n,r,i)=>{let a=Reflect.get(Object(i),`traceId`);if(typeof a!=`string`)return e(n,r);let c=t?(e,t)=>(s(n,r),l(r,a)(e,t)):l(r,a);o(n,r,c);let u=e(n,c);return()=>{u()}},d=n.off,f=(e,t)=>{t===void 0?d(e):d(e,s(e,t)??t)},p=n.on,_=n.once;return n.on=u(p,!1),n.once=u(_,!0),n.off=f,n},v=()=>{let e=[];return Object.assign(t=>{e.push(t)},{events:e,clear:()=>{e.length=0}})},y=()=>{},b=(e={})=>{let t=e.extension??globalThis.__REDUX_DEVTOOLS_EXTENSION__;if(!t)return y;let{starts:n=!1,depth:r=1,maxAge:i}=e,a=t.connect({name:e.name??`nanoeffects`,...i!==void 0&&{maxAge:i}}),o=/* @__PURE__ */ new Map,s=/* @__PURE__ */ new Map,c=()=>({running:Object.fromEntries(o)});return a.init(c()),({error:e,...t})=>{let i=(t.parentId===void 0?-1:s.get(t.parentId)??-1)+1,l=i<=r;t.phase===`start`?(s.set(t.id,i),l&&o.set(t.id,{type:t.type,effect:t.effect,...t.traceGroupId!==void 0&&{traceGroupId:t.traceGroupId}})):(s.delete(t.id),o.delete(t.id)),l&&(t.phase!==`start`||n)&&a.send({...t,type:`${t.type}/${t.effect}/${t.phase}`,event:t.type,...t.phase===`error`&&{error:e instanceof Error?e.message:e}},c())}},x=e=>{let t=typeof e==`function`?[e]:[...e??[]];return t.length===0?null:e=>{for(let r of t)try{r(e)}catch(e){n(`trace logger failed`,e)}}},S=()=>{},C=e=>{if(typeof e.traceGroupId==`string`)return e.traceGroupId;let t=p();if(typeof t!=`object`&&typeof t!=`function`||t===null)return;let n=Reflect.get(t,l),r=typeof n==`object`&&n?Reflect.get(n,`traceGroupId`):void 0;return typeof r==`string`?r:void 0},w=(e,t={})=>{let n=x(e),{filter:r,sample:i=1}=t,a=0,c=e=>typeof i==`function`?i({type:e.type,payload:e.payload}):Math.random()<i,l={task:(e,t)=>({id:++a,root:t?.root??a,parent:t?.id,type:e.type,payload:e.payload,sampled:t?.sampled??c(e),group:C(e)??t?.group}),rename:(e,t)=>{e.type=t},report:(e,t,i,a)=>{if(!e.sampled)return;let o={id:e.id,type:e.type,effect:t,phase:i,payload:e.payload};typeof e.parent==`number`&&(o.parentId=e.parent),e.root!==e.id&&(o.rootId=e.root),e.group!==void 0&&(o.traceGroupId=e.group),i===`error`&&(o.error=a),(!r||r(o))&&n?.(o)},settler:(e,t)=>{if(!e.sampled)return S;let n=!1;return(r,i)=>{n||(n=!0,l.report(e,t,r,i))}},run:(e,t,n,r)=>{if(!e.sampled)return r();let i=l.settler(e,t);l.report(e,t,`start`),o({signal:n},()=>i(`cancel`));let a;try{a=r()}catch(e){throw i(`error`,e),e}return s(a)?Promise.resolve(a).then(e=>(i(`done`),e),e=>{throw i(`error`,e),e}):(i(`done`),a)}};return l};export{u as consoleLogger,v as createTraceRecorder,w as createTracer,d as performanceLogger,b as reduxDevtools,_ as tracePlugin};
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { B as EventMap, d as Effects, o as Scope, s as WithFields } from "./action-creator-
|
|
2
|
-
import { t as BoundOf } from "./plugin-
|
|
1
|
+
import { B as EventMap, d as Effects, o as Scope, s as WithFields } from "./action-creator-9e8jesRa.js";
|
|
2
|
+
import { t as BoundOf } from "./plugin-DHkamZdH.js";
|
|
3
3
|
//#region src/scope/types.d.ts
|
|
4
4
|
/**
|
|
5
5
|
* The slots `scopePlugin` fills for `modulePlugin`. They are not on `Bus`: a bus
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{n as e}from"./context-
|
|
1
|
+
import{n as e}from"./context-CJGW6OWj.js";const t=Reflect.get(Symbol,`dispose`),n=n=>{let r=new AbortController,i=async(...t)=>{let i=t[0],{ctx:a,unlink:o}=e({event:{type:`withPolicy`,payload:i},parent:{signal:r.signal}});try{return await n(i,a)}finally{o()}},a=e=>{r.abort(e),r=new AbortController},o=Object.assign(i,{cancel:a});return t&&Reflect.set(o,t,()=>a()),o};export{n as t};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { B as EventMap,
|
|
1
|
+
import { B as EventMap, G as Task, U as PayloadOf } from "./action-creator-9e8jesRa.js";
|
|
2
2
|
//#region src/policies/with-policy.d.ts
|
|
3
3
|
/** What `withPolicy` returns: the task as a plain function that can be cancelled. */
|
|
4
4
|
type PolicyFunction<P, R> = {
|
package/docs/actions.md
CHANGED
|
@@ -118,7 +118,7 @@ The registry lives in `nanoeffects/actions`, so a bus without one carries none o
|
|
|
118
118
|
- When the task is aborted before the handler settles, emits `loadUser.cancel(reason)` instead of `success` or `fail`. After `pending`, exactly one of the three follows.
|
|
119
119
|
- `pending` / `success` / `fail` / `cancel` are a string (job makes an action creator) or an existing action creator. Missing ones become `<type>/pending`, `<type>/success`, `<type>/fail` or `<type>/cancel`.
|
|
120
120
|
- `bus.emit(loadUser(id))` returns a promise of the result. Handler errors are always handled: they go to `fail` and the promise resolves with `undefined`. For a result that must reject, use a command.
|
|
121
|
-
- Outcome actions are emitted as the task that ran the job (also for a handler bound with `commands.handle`). `success` and `fail` are not sent after abort; `cancel` is,
|
|
121
|
+
- Outcome actions are emitted as the task that ran the job (also for a handler bound with `commands.handle`). `success` and `fail` are not sent after abort; `cancel` is, at the moment of the abort.
|
|
122
122
|
- A missing handler is not an outcome: `emit` throws `No handler for command "..."` and nothing is sent.
|
|
123
123
|
- Calling the job only builds `{ type, payload }`; the handler runs on `emit`.
|
|
124
124
|
- The outcomes are events like any other: with `onUnhandled` set on the bus, it is called for a `pending` or a `cancel` that nobody listens to.
|
|
@@ -185,9 +185,16 @@ import { loadUser } from "./user";
|
|
|
185
185
|
bus.emit(loadUser("1"));
|
|
186
186
|
```
|
|
187
187
|
|
|
188
|
-
`cancel` is sent
|
|
188
|
+
`cancel` is sent at the moment of the abort, with the abort reason. A handler that ignores the signal and finishes later sends nothing more, so the flag is already `false`.
|
|
189
189
|
|
|
190
|
-
**
|
|
190
|
+
**With a policy.** A policy such as `latest`, `leading`, `debounce`, `throttle` or `queue` around the handler tells the job what it does with each call:
|
|
191
|
+
|
|
192
|
+
- `pending` is sent when the handler really starts: at once for `leading`, after the wait for `debounce`, when its turn comes for `queue`.
|
|
193
|
+
- A call that the policy drops before it starts sends nothing, not even `pending`. A second click that `leading` ignores does not clear the flag of the first.
|
|
194
|
+
- A run that `latest` replaces sends `cancel` before the next call sends `pending`.
|
|
195
|
+
- Every `pending` is followed by exactly one of `success`, `fail` and `cancel`, and nothing is sent without `pending`.
|
|
196
|
+
|
|
197
|
+
A flag is exact when calls do not overlap, or when `latest` replaces them. If several runs can go at once (`queue` with `concurrency` above 1, or a job without a policy called many times), keep a counter: add one on `pending` and take one off on `success`, `fail` and `cancel`. A policy that you write yourself, or that you hide in your own function, does not report to the job; `pending` is then sent at the call, as for a job with no policy.
|
|
191
198
|
|
|
192
199
|
## Mount domains with modules
|
|
193
200
|
|
|
@@ -318,7 +318,7 @@ bus.on(
|
|
|
318
318
|
## What is different
|
|
319
319
|
|
|
320
320
|
- **No state.** There is no `createStore`, `combine`, `restore`, `$store.map`. The bus holds listeners only. Take a store such as Zustand for state ([Stores](stores.md)).
|
|
321
|
-
- **`pending` is an action, not a store.** `createJob` sends `pending` when the handler starts, and `success`, `fail` or `cancel` when it ends; you keep the flag in your store ([Show a loading state](actions.md#show-a-loading-state-with-a-job)).
|
|
321
|
+
- **`pending` is an action, not a store.** `createJob` sends `pending` when the handler starts, and `success`, `fail` or `cancel` when it ends; you keep the flag in your store ([Show a loading state](actions.md#show-a-loading-state-with-a-job)). Policies report to the job, so the flag also follows `latest`, `leading`, `debounce`, `throttle` and `queue`; that section says when to count instead. A running task is also visible through [Tracing](tracing.md).
|
|
322
322
|
- **Cancellation is the default tool.** An Effector effect runs every call to the end. Here `latest` and `ctx.signal` stop what is no longer needed.
|
|
323
323
|
- **Events are matched by name, not by identity.** An event is a string or a `createAction` creator, not a unit that you import and call. Two modules agree on the name.
|
|
324
324
|
- **No graph.** `sample` and `forward` build a static graph. A bus subscribes handlers at runtime and the call order is the order of `on`.
|
package/docs/oop.md
CHANGED
|
@@ -194,6 +194,8 @@ Things to know:
|
|
|
194
194
|
- On a class that `extendBus` did not make, a decorator does nothing.
|
|
195
195
|
- Both the decorators of the language and `experimentalDecorators` work. Your compiler has to support the one you use: TypeScript 5 or newer for the first, and the `experimentalDecorators` option for the second.
|
|
196
196
|
|
|
197
|
+
Name a method for the [trace](tracing.md#name-a-listener) with `{ traceId }`, as the second argument or, after a wrapper, the third: `@On(queryChanged, { traceId: "searcher" })` or `@On(queryChanged, latest, { traceId: "searcher" })`. It needs `tracePlugin` on the bus and is ignored without it.
|
|
198
|
+
|
|
197
199
|
## Decorate the class with `@WithBus`
|
|
198
200
|
|
|
199
201
|
`@WithBus(bus)` does what `extendBus(bus, Base)` does, as a class decorator. `@WithBus()` makes a bus for the class.
|
package/docs/package.md
CHANGED
|
@@ -16,7 +16,7 @@ Imports are split so you only load what you use. `createBus` stays small; the re
|
|
|
16
16
|
| `nanoeffects/observable` | `createObserve` |
|
|
17
17
|
| `nanoeffects/react` | `reactPlugin`: adds the `useEmitter` hook to a bus (needs React 18 or newer) |
|
|
18
18
|
| `nanoeffects/dev` | `devPlugin` (no-op in production) |
|
|
19
|
-
| `nanoeffects/trace` | `createTracer
|
|
19
|
+
| `nanoeffects/trace` | `createTracer`, the loggers and `tracePlugin` (names for the trace) |
|
|
20
20
|
|
|
21
21
|
The `...Plugin` names above are used with `bus.use`. [Plugins](plugins.md) lists all of them, what each returns, and the order to use them in.
|
|
22
22
|
|
package/docs/plugins.md
CHANGED
|
@@ -95,6 +95,7 @@ Add one of these when you meet its need. None of them is required.
|
|
|
95
95
|
| [`signalPlugin`](#tie-an-emit-to-an-outside-signal-signalplugin) | `emit(call, { signal })` that aborts its tasks when an outside signal aborts. | `nanoeffects/signal` | The same bus, typed with the new `emit` |
|
|
96
96
|
| [`matchPlugin`](#listen-to-a-group-of-events-matchplugin) | `on` that listens to a group of events which a function picks. | `nanoeffects/match` | The same bus, typed with the new overloads |
|
|
97
97
|
| [`emitterPlugin`](#hand-the-bus-to-a-state-manager-emitterplugin) | A callback that emits an action, to give to a state manager. | `nanoeffects/actions` | The same bus, with `emitter` |
|
|
98
|
+
| [`tracePlugin`](#name-the-origin-and-the-flow-of-a-trace-traceplugin) | `traceId` and `traceGroupId` for a trace: the root of an emitter, a flow, a named listener. | `nanoeffects/trace` | The same bus |
|
|
98
99
|
| [`reactPlugin`](#tell-the-bus-when-a-react-value-changes-reactplugin) | A React hook that emits when a value of a component changes. | `nanoeffects/react` | The same bus, with `useEmitter` |
|
|
99
100
|
| [`devPlugin`](#find-leaks-while-you-develop-devplugin) | Warnings about listeners that pile up, and messages about modules, while you develop. | `nanoeffects/dev` | A function that disconnects it |
|
|
100
101
|
|
|
@@ -138,6 +139,20 @@ bus.emit(getUser("1"), { signal: controller.signal }); // runs the command
|
|
|
138
139
|
controller.abort(); // ctx.signal of the handler aborts with it
|
|
139
140
|
```
|
|
140
141
|
|
|
142
|
+
### Name the origin and the flow of a trace: `tracePlugin`
|
|
143
|
+
|
|
144
|
+
With a tracer on the bus, the plugin lets a trace say which subscription began a chain (`traceId` of `useEmitter` and `bus.emitter`), follow one flow by a `traceGroupId`, and show which listener ran (`bus.on(event, handler, { traceId })`). Without the plugin the options are ignored. More in [Tracing](tracing.md#show-which-subscription-began-a-chain).
|
|
145
|
+
|
|
146
|
+
```js
|
|
147
|
+
import { createBus } from "nanoeffects";
|
|
148
|
+
import { consoleLogger, createTracer, tracePlugin } from "nanoeffects/trace";
|
|
149
|
+
|
|
150
|
+
// tracePlugin — names the roots, groups and listeners of the trace
|
|
151
|
+
const bus = createBus({ trace: createTracer(consoleLogger()) }).use(tracePlugin());
|
|
152
|
+
|
|
153
|
+
bus.on("name/changed", saveName, { traceId: "saveNotifier" }); // a listener you can find in the log
|
|
154
|
+
```
|
|
155
|
+
|
|
141
156
|
### Listen to a group of events: `matchPlugin`
|
|
142
157
|
|
|
143
158
|
`on`, `once` and `off` take a function that picks the events, such as every `user/*` event. A type guard narrows the payload. The subscription listens to every event, so for a few known events `on(creator, handler)` is cheaper. More in the [Guide](guide.md#pick-events-with-a-function).
|
|
@@ -174,7 +189,7 @@ $name.listen(bus.emitter(nameChanged)); // every change of $name emits nameChang
|
|
|
174
189
|
|
|
175
190
|
### Tell the bus when a React value changes: `reactPlugin`
|
|
176
191
|
|
|
177
|
-
`useEmitter(event, value)` emits after a render commits with a new value. It does not emit on mount, and not twice under StrictMode. It needs React 18 or newer. More in [Stores](stores.md#react-sharing-a-value-across-components).
|
|
192
|
+
`useEmitter(event, value, options?)` emits after a render commits with a new value. It does not emit on mount, and not twice under StrictMode. The options are `{ equals, traceId, traceGroupId }`; the last two name the emit in the [trace](tracing.md#show-which-subscription-began-a-chain). It needs React 18 or newer. More in [Stores](stores.md#react-sharing-a-value-across-components).
|
|
178
193
|
|
|
179
194
|
```jsx
|
|
180
195
|
import { useState } from "react";
|
package/docs/scope.md
CHANGED
|
@@ -189,7 +189,7 @@ When several places set the same field, the strongest one wins:
|
|
|
189
189
|
| 3 | the scope of the module that owns the handler |
|
|
190
190
|
| 4 (weakest) | the bus: `createBus({ context })`, `contextPlugin`, `effectsPlugin` |
|
|
191
191
|
|
|
192
|
-
The fields of the library (`signal`, `abort`, `emit`, `on`, `off`, `run`, `type`, `payload`) are never replaced. A child task (`ctx.run`, an attempt of `retry`) has the fields of its parent.
|
|
192
|
+
The fields of the library (`signal`, `abort`, `emit`, `on`, `off`, `run`, `type`, `payload`) are never replaced. The name `traceGroupId` is reserved: the tracer reads it, and it is not put on `ctx` ([Follow one flow](tracing.md#follow-one-flow-with-a-tracegroupid)). A child task (`ctx.run`, an attempt of `retry`) has the fields of its parent.
|
|
193
193
|
|
|
194
194
|
## Keep a generic effect generic
|
|
195
195
|
|
package/docs/stores.md
CHANGED
|
@@ -83,6 +83,10 @@ String event names (`"user/requested"`) work the same. Use your usual RTK action
|
|
|
83
83
|
|
|
84
84
|
The only option is `filter`, which keeps rejected actions away from the bus. Options of the bus (`onError`, `context`, `trace`) go to `createBus`. Use one bus for one store. Values that are not plain actions (thunks) go through untouched. Nothing here depends on the `redux` package at runtime.
|
|
85
85
|
|
|
86
|
+
### Show which dispatch began a chain
|
|
87
|
+
|
|
88
|
+
With a tracer and `tracePlugin` on the bus, each dispatched action reaches the bus from a root task of the trace. Name it with `traceId`, and put the flow in a group with `traceGroupId`: `createEffectsMiddleware(bus, { traceId: "store", traceGroupId: "checkout" })`. Without a `traceId` the root has the type of the action. Without the plugin the options are ignored. More in [Tracing](tracing.md#show-which-subscription-began-a-chain).
|
|
89
|
+
|
|
86
90
|
### Type `ctx.store` (optional)
|
|
87
91
|
|
|
88
92
|
Only if you want TypeScript to know `store` on handlers. **Skip this in JavaScript** — the middleware already puts `store` on the task at runtime. These lines do not connect the store across the app.
|
|
@@ -461,7 +465,7 @@ export function Results() {
|
|
|
461
465
|
Two limits to know:
|
|
462
466
|
|
|
463
467
|
- **All consumers re-render** on any change of the context value. Split it into two contexts (`query` and `items`) if that is slow.
|
|
464
|
-
- **A new object counts as a change.** For a value that is rebuilt with the same content, pass
|
|
468
|
+
- **A new object counts as a change.** For a value that is rebuilt with the same content, pass `equals` in the options, the third argument, to say when two values are the same: `useEmitter(profileChanged, profile, { equals: (previous, next) => previous.id === next.id })`. The same object takes `traceId` and `traceGroupId`, which name the subscription and the flow in the [trace](tracing.md#show-which-subscription-began-a-chain).
|
|
465
469
|
|
|
466
470
|
`useEmitter` emits after the render, not at the moment of `setQuery`. To emit on every call, even with the same value, call an emitter from the event handler (`bus.emitter(action)`, see [Zustand](#zustand)) instead.
|
|
467
471
|
|