lanka 1.0.0 → 1.1.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 +5 -3
- package/dist/{ALankaGateway-ExlRGT3D.d.ts → ALankaGateway-CkW1LbKE.d.ts} +50 -4
- package/dist/{ILankaScenarioMetadata-Bu-yggTZ.d.ts → ILankaScenarioMetadata-GoWWNEQL.d.ts} +1 -1
- package/dist/{ILankaScenarioVM-DuCyPoyT.d.ts → ILankaScenarioVM-DUsI-fSc.d.ts} +116 -3
- package/dist/{LankaScenarioLocator-BGQHwf3n.d.ts → LankaScenarioLocator-D86TIwiu.d.ts} +11 -6
- package/dist/{LankaSharedStoreLocator-MvCpav5F.d.ts → LankaSharedStoreLocator-zS2kLu-S.d.ts} +21 -0
- package/dist/_extend/index.d.ts +7 -7
- package/dist/_extend/index.js +3 -3
- package/dist/_internal/index.d.ts +6 -6
- package/dist/{activeRuntime-FcsSJvUg.d.ts → activeRuntime-B336NU5I.d.ts} +3 -3
- package/dist/bootstrap/index.d.ts +14 -145
- package/dist/bootstrap/index.js +5 -5
- package/dist/{chunk-FIR4XTBL.js → chunk-5MAQVBI2.js} +27 -24
- package/dist/chunk-5MAQVBI2.js.map +1 -0
- package/dist/chunk-D5WKKEIR.js +54 -0
- package/dist/chunk-D5WKKEIR.js.map +1 -0
- package/dist/{chunk-RYFZCAQ3.js → chunk-LMKLLEHA.js} +111 -25
- package/dist/chunk-LMKLLEHA.js.map +1 -0
- package/dist/{chunk-EWVDJYCC.js → chunk-O5ROO7QF.js} +28 -9
- package/dist/chunk-O5ROO7QF.js.map +1 -0
- package/dist/{chunk-ILQNYQY5.js → chunk-UE2C76OR.js} +32 -18
- package/dist/chunk-UE2C76OR.js.map +1 -0
- package/dist/{chunk-Q3SOVBIJ.js → chunk-UGXSGQPW.js} +8 -4
- package/dist/chunk-UGXSGQPW.js.map +1 -0
- package/dist/createLanka-DI1CSy2Q.d.ts +139 -0
- package/dist/{createLankaScope-Bc_vChRs.d.ts → createLankaScope-BiFxNQgl.d.ts} +1 -1
- package/dist/gateway/index.d.ts +77 -67
- package/dist/gateway/index.js +51 -56
- package/dist/gateway/index.js.map +1 -1
- package/dist/index.d.ts +9 -8
- package/dist/index.js +5 -5
- package/dist/locator/index.d.ts +7 -55
- package/dist/locator/index.js +1 -1
- package/dist/scenario/index.d.ts +6 -4
- package/dist/scenario/index.js +2 -2
- package/dist/stream/index.d.ts +386 -0
- package/dist/stream/index.js +287 -0
- package/dist/stream/index.js.map +1 -0
- package/dist/validation/index.js +4 -48
- package/dist/validation/index.js.map +1 -1
- package/dist/viewmodel/index.d.ts +1 -1
- package/dist/viewmodel/index.js +4 -2
- package/dist/viewmodel/index.js.map +1 -1
- package/package.json +7 -3
- package/skills/lanka-core/SKILL.md +1 -1
- package/skills/lanka-core/reference.md +110 -17
- package/skills/lanka-packages/SKILL.md +1 -1
- package/dist/chunk-EWVDJYCC.js.map +0 -1
- package/dist/chunk-FIR4XTBL.js.map +0 -1
- package/dist/chunk-ILQNYQY5.js.map +0 -1
- package/dist/chunk-Q3SOVBIJ.js.map +0 -1
- package/dist/chunk-RYFZCAQ3.js.map +0 -1
package/README.md
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
**◆ core** · Core
|
|
4
4
|
|
|
5
|
-
>
|
|
5
|
+
> Twelve subsystems, two peer dependencies, five extension points.
|
|
6
6
|
|
|
7
7
|
One, unscoped. Everything depends on it; it depends on nothing.
|
|
8
8
|
|
|
@@ -16,7 +16,8 @@ One, unscoped. Everything depends on it; it depends on nothing.
|
|
|
16
16
|
| --- | --- | --- |
|
|
17
17
|
| `useRequestMiddleware(mw)` | wrap every request | yes |
|
|
18
18
|
| `inFlight.subscribe(fn)` | observe the number of requests on the wire | yes |
|
|
19
|
-
| `lankaEventBus.addMiddleware` | intercept bus events | yes |
|
|
19
|
+
| `lankaEventBus.addMiddleware` | intercept bus events, and stop one | yes |
|
|
20
|
+
| `lankaEventBus.addObserver` | hear what became of each dispatch | yes |
|
|
20
21
|
| `LankaLogger sinks` | where log output goes | yes |
|
|
21
22
|
| `use(plugin)` | register a whole plugin | yes |
|
|
22
23
|
|
|
@@ -46,6 +47,7 @@ the seal on `internal`, and catches a subsystem added as a folder and forgotten
|
|
|
46
47
|
- `src/mock/`
|
|
47
48
|
- `src/errors/`
|
|
48
49
|
- `src/scenario/`
|
|
50
|
+
- `src/stream/`
|
|
49
51
|
- `src/viewmodel/`
|
|
50
52
|
- `src/logger/`
|
|
51
53
|
- `src/internal/` — **not exported.** Refactored without a major.
|
|
@@ -226,7 +228,7 @@ to rename.
|
|
|
226
228
|
|
|
227
229
|
`ViewModel` shortens to `VM` in class, factory and type names: `ALankaVM` and
|
|
228
230
|
`createLankaVM` are written in every screen file — the same ViewModel reached from
|
|
229
|
-
either style, one of the
|
|
231
|
+
either style, one of the roles `skills/parity/SKILL.md` governs.
|
|
230
232
|
|
|
231
233
|
Three names stay bare — `isRecord`, `getStringField`, `generateUuid`. They are pure
|
|
232
234
|
utilities over ordinary values; a collision there is resolved at the import site, which
|
|
@@ -1,5 +1,34 @@
|
|
|
1
1
|
import { I as ILankaValidator } from './lankaStandardValidator-CL-r-zEV.js';
|
|
2
2
|
|
|
3
|
+
/**
|
|
4
|
+
* `RequestInit`, with the body a JSON API actually sends.
|
|
5
|
+
*
|
|
6
|
+
* `RequestInit["body"]` is `BodyInit | null` — a string, a `FormData`, a blob,
|
|
7
|
+
* bytes. It is what `fetch` accepts and it is NOT what a gateway method writes:
|
|
8
|
+
* every one of them writes `body: { name, email }`, an object, and lets the
|
|
9
|
+
* transport encode it.
|
|
10
|
+
*
|
|
11
|
+
* The framework's transport has always encoded that object. The TYPE never
|
|
12
|
+
* admitted it, and the cost was not a cast at the call site — it was a fork. A
|
|
13
|
+
* consumer could not write `body: { … }` against `RequestInit`, so they declared
|
|
14
|
+
* their own options type; declaring it made every shipped transport
|
|
15
|
+
* unassignable, because those were fixed to `RequestInit`; so they wrote a
|
|
16
|
+
* transport too, and with it a base URL, a CSRF header and an auth refresh the
|
|
17
|
+
* framework already had. One wrong type produced a re-implementation of three
|
|
18
|
+
* packages.
|
|
19
|
+
*
|
|
20
|
+
* `unknown` rather than a union of the encodable shapes: the transport decides
|
|
21
|
+
* by INSPECTING the value, and a type listing what it accepts would have to be
|
|
22
|
+
* kept in step with that inspection by hand. What is not a `BodyInit` is JSON —
|
|
23
|
+
* that is the whole rule, and it needs no enumeration.
|
|
24
|
+
*/
|
|
25
|
+
type TLankaRequestInit = Omit<RequestInit, "body"> & {
|
|
26
|
+
/**
|
|
27
|
+
* Anything. A `BodyInit` travels as given; everything else is encoded as JSON.
|
|
28
|
+
*/
|
|
29
|
+
body?: unknown;
|
|
30
|
+
};
|
|
31
|
+
|
|
3
32
|
/**
|
|
4
33
|
* Transport options plus what core controls.
|
|
5
34
|
*
|
|
@@ -26,7 +55,7 @@ type TLankaExecuteOptions<TOptions> = TOptions & {
|
|
|
26
55
|
* is how development without a backend works, and a request that ignored it
|
|
27
56
|
* would silently disable mock mode for the gateway holding it.
|
|
28
57
|
*/
|
|
29
|
-
interface ILankaRequest<TOptions =
|
|
58
|
+
interface ILankaRequest<TOptions = TLankaRequestInit> {
|
|
30
59
|
/**
|
|
31
60
|
* Sends the request and returns the value the caller asked for.
|
|
32
61
|
*
|
|
@@ -68,7 +97,15 @@ interface IALankaGatewayConfig<TOptions> {
|
|
|
68
97
|
* reads it.
|
|
69
98
|
*/
|
|
70
99
|
queryParamsHandler?: TLankaQueryBuilder;
|
|
71
|
-
/**
|
|
100
|
+
/**
|
|
101
|
+
* The validator a method checks a response body with. Defaults to
|
|
102
|
+
* `lankaStandardValidator`.
|
|
103
|
+
*
|
|
104
|
+
* Reachable as `this.validationService` in a class and as
|
|
105
|
+
* `validationService` in the functional context. A test hands one that
|
|
106
|
+
* records what it was asked; a migration hands one that accepts a shape the
|
|
107
|
+
* new schema does not yet.
|
|
108
|
+
*/
|
|
72
109
|
validationService?: ILankaValidator;
|
|
73
110
|
/**
|
|
74
111
|
* Enable mock mode. If undefined, reads from infrastructure flags (isMockMode).
|
|
@@ -77,9 +114,18 @@ interface IALankaGatewayConfig<TOptions> {
|
|
|
77
114
|
useMock?: boolean;
|
|
78
115
|
}
|
|
79
116
|
|
|
80
|
-
declare abstract class ALankaGateway<TOptions =
|
|
117
|
+
declare abstract class ALankaGateway<TOptions = TLankaRequestInit> {
|
|
81
118
|
protected requestExecutor: ILankaRequest<TOptions>;
|
|
82
119
|
protected queryParamsHandler: TLankaQueryBuilder;
|
|
120
|
+
/**
|
|
121
|
+
* The validator a method checks a response body with.
|
|
122
|
+
*
|
|
123
|
+
* `config.validationService` when one was given, the Standard Schema port
|
|
124
|
+
* otherwise. It used to be accepted by the config and read by nothing: a
|
|
125
|
+
* consumer handing a test double to the gateway got the real validator and no
|
|
126
|
+
* error, which is the worst kind of ignored option — it looks honoured.
|
|
127
|
+
*/
|
|
128
|
+
protected readonly validationService: ILankaValidator;
|
|
83
129
|
protected readonly useMock: boolean;
|
|
84
130
|
protected readonly basePath: string;
|
|
85
131
|
protected constructor(config: IALankaGatewayConfig<TOptions>);
|
|
@@ -119,4 +165,4 @@ declare abstract class ALankaGateway<TOptions = RequestInit> {
|
|
|
119
165
|
protected setQueryParamsHandler(handler: TLankaQueryBuilder): void;
|
|
120
166
|
}
|
|
121
167
|
|
|
122
|
-
export { ALankaGateway as A, type IALankaGatewayConfig as I, type TLankaExecuteOptions as T, type
|
|
168
|
+
export { ALankaGateway as A, type IALankaGatewayConfig as I, type TLankaExecuteOptions as T, type TLankaRequestInit as a, type ILankaRequest as b, type TLankaQueryBuilder as c, type TLankaQueryParams as d };
|
|
@@ -35,6 +35,17 @@ interface ILankaEventLog {
|
|
|
35
35
|
eventType: string;
|
|
36
36
|
/** ISO timestamp of when the event was dispatched. */
|
|
37
37
|
timestamp: string;
|
|
38
|
+
/**
|
|
39
|
+
* Where this record falls in the order the bus saw events, counting from one.
|
|
40
|
+
*
|
|
41
|
+
* What `getEventLogs()` orders by, and the reason it can: a timestamp has
|
|
42
|
+
* millisecond resolution, and a burst dispatches many events inside one, so
|
|
43
|
+
* two records of one millisecond cannot be told apart by their time.
|
|
44
|
+
*
|
|
45
|
+
* Optional because a record built by anything other than the bus has no
|
|
46
|
+
* place in that order.
|
|
47
|
+
*/
|
|
48
|
+
sequence?: number;
|
|
38
49
|
/** The payload data of the event. */
|
|
39
50
|
data: unknown;
|
|
40
51
|
/** Optional captured stack trace (if enabled). */
|
|
@@ -77,6 +88,60 @@ type TLankaEventBusDecision = "pass" | {
|
|
|
77
88
|
*/
|
|
78
89
|
type TLankaEventBusMiddleware<T> = (eventType: string, data: T) => TLankaEventBusDecision;
|
|
79
90
|
|
|
91
|
+
/**
|
|
92
|
+
* What became of one dispatch, after the whole chain has run.
|
|
93
|
+
*
|
|
94
|
+
* The counterpart of `TLankaEventBusDecision`: a middleware RETURNS a decision,
|
|
95
|
+
* and the bus REPORTS an outcome. The two are deliberately symmetrical, and the
|
|
96
|
+
* asymmetry that matters is that an outcome cannot change anything.
|
|
97
|
+
*/
|
|
98
|
+
interface ILankaEventBusOutcome {
|
|
99
|
+
eventType: string;
|
|
100
|
+
/**
|
|
101
|
+
* Delivered to the subscribers, stopped by a middleware, or refused by the
|
|
102
|
+
* event's own schema.
|
|
103
|
+
*
|
|
104
|
+
* A union rather than an `enum`: a fourth outcome is then additive, which
|
|
105
|
+
* `skills/surface/SKILL.md` §6d.5 is about.
|
|
106
|
+
*/
|
|
107
|
+
outcome: "delivered" | "stopped" | "invalid";
|
|
108
|
+
/**
|
|
109
|
+
* How many subscribers the event had when it was dispatched.
|
|
110
|
+
*
|
|
111
|
+
* The AUDIENCE, not the recipients: "three subscribers never heard it" is the
|
|
112
|
+
* sentence a stopped event needs, and a count that went to zero on a stop
|
|
113
|
+
* could not say it.
|
|
114
|
+
*/
|
|
115
|
+
subscribers: number;
|
|
116
|
+
/** The reason a middleware gave, when one stopped it. */
|
|
117
|
+
stoppedBy?: string;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
/**
|
|
121
|
+
* Something watching what became of each dispatch.
|
|
122
|
+
*
|
|
123
|
+
* ## Why this is not a middleware
|
|
124
|
+
*
|
|
125
|
+
* A middleware runs in a CHAIN and sees only what happened before it. The first
|
|
126
|
+
* one registered — which is what a diagnostic tool ends up being, since it is
|
|
127
|
+
* installed at bootstrap — cannot see a later middleware's decision to stop an
|
|
128
|
+
* event, so "which middleware stopped it" was a question nothing could answer.
|
|
129
|
+
* `@lankajs/plugin-devtools` carried a `stoppedBy` field that no code path ever
|
|
130
|
+
* filled, and its guide documented it.
|
|
131
|
+
*
|
|
132
|
+
* An observer runs ONCE per dispatch, after the chain, and its return value is
|
|
133
|
+
* ignored — it cannot decide anything. That is what keeps a diagnostic tool
|
|
134
|
+
* incapable of changing what it diagnoses, by construction rather than by
|
|
135
|
+
* discipline.
|
|
136
|
+
*
|
|
137
|
+
* ## Why the parameter is one object
|
|
138
|
+
*
|
|
139
|
+
* `skills/surface/SKILL.md` §6d.9: a callback's parameters are one object, so
|
|
140
|
+
* the day the bus learns to report how long delivery took, nobody's handler
|
|
141
|
+
* silently receives a different third argument.
|
|
142
|
+
*/
|
|
143
|
+
type TLankaEventBusObserver = (outcome: ILankaEventBusOutcome) => void;
|
|
144
|
+
|
|
80
145
|
/**
|
|
81
146
|
* How many recent values to replay to a new subscriber.
|
|
82
147
|
*
|
|
@@ -88,12 +153,26 @@ declare class LankaEventBusInstance {
|
|
|
88
153
|
private registry;
|
|
89
154
|
/** Middleware registered on this instance. */
|
|
90
155
|
private middlewares;
|
|
156
|
+
/**
|
|
157
|
+
* What is watching the OUTCOME of each dispatch — see `TLankaEventBusObserver`.
|
|
158
|
+
*
|
|
159
|
+
* An array rather than a set for one reason: `dispatch` reads `.length` on
|
|
160
|
+
* every event, and that check is what keeps an unobserved bus paying nothing.
|
|
161
|
+
*/
|
|
162
|
+
private observers;
|
|
91
163
|
/** Default maximum number of logs kept per event type. */
|
|
92
164
|
private defaultMaxLogs;
|
|
93
165
|
/** Internal timers for replay batching (avoid multiple replays in the same tick). */
|
|
94
166
|
private pendingReplayTimers;
|
|
95
167
|
/** Whether event logging is enabled. */
|
|
96
168
|
private isEnableLogs;
|
|
169
|
+
/**
|
|
170
|
+
* How many events this bus has logged, ever — the order records are read in.
|
|
171
|
+
*
|
|
172
|
+
* Incremented only while logging is on, which is off by default, so a bus
|
|
173
|
+
* nobody is inspecting pays nothing for it.
|
|
174
|
+
*/
|
|
175
|
+
private dispatchCount;
|
|
97
176
|
/** Configures the bus, e.g. logging. Called once at application start. */
|
|
98
177
|
enableLogs(): void;
|
|
99
178
|
disableLogs(): void;
|
|
@@ -162,7 +241,28 @@ declare class LankaEventBusInstance {
|
|
|
162
241
|
/** Removes previously added middleware. */
|
|
163
242
|
removeMiddleware<T>(mw: TLankaEventBusMiddleware<T>): void;
|
|
164
243
|
/**
|
|
165
|
-
*
|
|
244
|
+
* Watches what became of each dispatch. An extension point — the sixth.
|
|
245
|
+
*
|
|
246
|
+
* An observer never decides: its return value is ignored, and a throw from it
|
|
247
|
+
* is logged rather than surfaced. A diagnostic tool that could stop an event
|
|
248
|
+
* would make "I disabled the inspector and it started working" a sentence
|
|
249
|
+
* somebody says.
|
|
250
|
+
*/
|
|
251
|
+
addObserver(observer: TLankaEventBusObserver): void;
|
|
252
|
+
/** Removes a previously added observer. */
|
|
253
|
+
removeObserver(observer: TLankaEventBusObserver): void;
|
|
254
|
+
/**
|
|
255
|
+
* Log of dispatched events, oldest first, `limit` most recent kept.
|
|
256
|
+
*
|
|
257
|
+
* ## Why the records are sorted rather than concatenated
|
|
258
|
+
*
|
|
259
|
+
* They are held per event TYPE, so that each type keeps its own `maxLogs`
|
|
260
|
+
* and a chatty event cannot push a quiet one's history out. Concatenating
|
|
261
|
+
* those lists puts every record of one type before every record of the next,
|
|
262
|
+
* and `slice(-limit)` then answers the tail of whichever type the registry
|
|
263
|
+
* happened to hold last — not the most recent events at all. On a bus with
|
|
264
|
+
* one event type nothing looked wrong; on a real one the log was a
|
|
265
|
+
* chronology that had never been in chronological order.
|
|
166
266
|
*
|
|
167
267
|
* @param eventType Limit to one type
|
|
168
268
|
* @param limit How many recent records to return
|
|
@@ -172,8 +272,21 @@ declare class LankaEventBusInstance {
|
|
|
172
272
|
clearEvent(eventType: string): void;
|
|
173
273
|
/** Removes every event and any scheduled replays. */
|
|
174
274
|
clearAllEvents(): void;
|
|
175
|
-
/** Full bus reset: events and
|
|
275
|
+
/** Full bus reset: events, middleware and observers. */
|
|
176
276
|
reset(): void;
|
|
277
|
+
/**
|
|
278
|
+
* Tells the observers what became of a dispatch.
|
|
279
|
+
*
|
|
280
|
+
* The empty-list check is the whole reason a bus nobody watches pays nothing
|
|
281
|
+
* for this: `dispatch` is a hot path, and an iteration over an empty array on
|
|
282
|
+
* every event would be a cost paid by every application for a feature almost
|
|
283
|
+
* none of them installs. Measured in `LankaEventBusInstance.bench.ts`.
|
|
284
|
+
*
|
|
285
|
+
* An observer that throws is logged and the next one still runs — the same
|
|
286
|
+
* treatment a subscriber gets, and for the same reason: a diagnostic tool must
|
|
287
|
+
* not be able to break the application it is diagnosing.
|
|
288
|
+
*/
|
|
289
|
+
private report;
|
|
177
290
|
/**
|
|
178
291
|
* Marks the last log record with the reason it was stopped.
|
|
179
292
|
*
|
|
@@ -257,4 +370,4 @@ interface ILankaScenarioVM {
|
|
|
257
370
|
resetScenario(): void;
|
|
258
371
|
}
|
|
259
372
|
|
|
260
|
-
export { type ILankaScenarioVM as I, LankaEventBusInstance as L, type TLankaReplayRequest as T, type ILankaScenario as a, type ILankaEventMetadata as b, type TLankaEventBusMiddleware as c, type
|
|
373
|
+
export { type ILankaScenarioVM as I, LankaEventBusInstance as L, type TLankaReplayRequest as T, type ILankaScenario as a, type ILankaEventMetadata as b, type TLankaEventBusMiddleware as c, type TLankaEventBusObserver as d, type ILankaEventLog as e, type ILankaEventBusOutcome as f, type TLankaEventBusDecision as g };
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import { a as ILankaScenario, I as ILankaScenarioVM } from './ILankaScenarioVM-
|
|
2
|
-
import { I as ILankaScenarioMetadata } from './ILankaScenarioMetadata-
|
|
3
|
-
import { A as ALankaGateway } from './ALankaGateway-
|
|
4
|
-
import { A as ALankaLocator } from './LankaSharedStoreLocator-
|
|
1
|
+
import { a as ILankaScenario, I as ILankaScenarioVM } from './ILankaScenarioVM-DUsI-fSc.js';
|
|
2
|
+
import { I as ILankaScenarioMetadata } from './ILankaScenarioMetadata-GoWWNEQL.js';
|
|
3
|
+
import { A as ALankaGateway } from './ALankaGateway-CkW1LbKE.js';
|
|
4
|
+
import { A as ALankaLocator } from './LankaSharedStoreLocator-zS2kLu-S.js';
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* The scenario registry: both those that registered themselves and those
|
|
@@ -31,7 +31,8 @@ declare class LankaScenariosRegistry {
|
|
|
31
31
|
*/
|
|
32
32
|
register(scenario: ILankaScenario<unknown>): boolean;
|
|
33
33
|
/**
|
|
34
|
-
*
|
|
34
|
+
* Removes a scenario, calling its `cleanup` if it declared one.
|
|
35
|
+
*
|
|
35
36
|
* @param scenarioName Name of the scenario to unregister
|
|
36
37
|
* @returns true if unregistered successfully, false if not found
|
|
37
38
|
*/
|
|
@@ -61,7 +62,11 @@ declare class LankaScenariosRegistry {
|
|
|
61
62
|
/** Every registered ViewModel. */
|
|
62
63
|
getAllViewModels(): ILankaScenarioVM[];
|
|
63
64
|
/**
|
|
64
|
-
*
|
|
65
|
+
* Removes every scenario, calling each one's `cleanup`.
|
|
66
|
+
*
|
|
67
|
+
* What `dispose()` and the between-tests reset go through: `initialize` ran
|
|
68
|
+
* for every scenario at bootstrap, and this is the one moment its mirror
|
|
69
|
+
* image can run for all of them.
|
|
65
70
|
*/
|
|
66
71
|
clear(): void;
|
|
67
72
|
}
|
package/dist/{LankaSharedStoreLocator-MvCpav5F.d.ts → LankaSharedStoreLocator-zS2kLu-S.d.ts}
RENAMED
|
@@ -43,6 +43,27 @@ declare abstract class ALankaLocator<TInstance> implements ILankaLocator<TInstan
|
|
|
43
43
|
notFoundError: (name: string, propertyName: string) => string;
|
|
44
44
|
};
|
|
45
45
|
protected constructor(config: ILankaLocatorConfig<TInstance>);
|
|
46
|
+
/**
|
|
47
|
+
* The class a name resolves to: hand-registered FIRST, then the consumer's
|
|
48
|
+
* barrel.
|
|
49
|
+
*
|
|
50
|
+
* One owner for both callers, and that is the whole point of it existing.
|
|
51
|
+
* `registeredClasses` used to be read inside each locator's own
|
|
52
|
+
* `findClassByName`, and only two of the four did it — singletons and shared
|
|
53
|
+
* stores worked, gateways and scenarios silently dropped the class. Moving the
|
|
54
|
+
* read into `getInstanceByName` fixed those two and broke a third path:
|
|
55
|
+
* `LankaSingletonLocator.createScopedInstance` calls `findClassByName`
|
|
56
|
+
* directly, so a registered class stopped resolving inside a scope. Ten tests
|
|
57
|
+
* said so.
|
|
58
|
+
*
|
|
59
|
+
* Both callers go through here now. A fourth caller added later gets the
|
|
60
|
+
* precedence for free instead of having to remember it.
|
|
61
|
+
*
|
|
62
|
+
* The precedence itself matches `registeredInstances` below: what a caller
|
|
63
|
+
* handed over wins over what the barrel happens to export under that name,
|
|
64
|
+
* because the caller is usually a test substituting a double.
|
|
65
|
+
*/
|
|
66
|
+
protected classFor(instanceName: string): (new () => TInstance) | undefined;
|
|
46
67
|
/**
|
|
47
68
|
* An object by class name.
|
|
48
69
|
*
|
package/dist/_extend/index.d.ts
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
export { L as LankaGatewayLocator, a as LankaScenarioLocator, b as LankaScenarioVMRegistry, c as LankaScenariosRegistry } from '../LankaScenarioLocator-
|
|
2
|
-
import { a as ILankaLocator } from '../LankaSharedStoreLocator-
|
|
3
|
-
export { A as ALankaLocator, L as LankaSharedStoreLocator, b as LankaSingletonLocator } from '../LankaSharedStoreLocator-
|
|
4
|
-
export { c as createLankaScope } from '../createLankaScope-
|
|
1
|
+
export { L as LankaGatewayLocator, a as LankaScenarioLocator, b as LankaScenarioVMRegistry, c as LankaScenariosRegistry } from '../LankaScenarioLocator-D86TIwiu.js';
|
|
2
|
+
import { a as ILankaLocator } from '../LankaSharedStoreLocator-zS2kLu-S.js';
|
|
3
|
+
export { A as ALankaLocator, L as LankaSharedStoreLocator, b as LankaSingletonLocator } from '../LankaSharedStoreLocator-zS2kLu-S.js';
|
|
4
|
+
export { c as createLankaScope } from '../createLankaScope-BiFxNQgl.js';
|
|
5
5
|
export { c as composeLankaRequestMiddleware } from '../lankaRequestMiddleware-DAC5kCb7.js';
|
|
6
|
-
import '../ILankaScenarioVM-
|
|
7
|
-
import '../ILankaScenarioMetadata-
|
|
8
|
-
import '../ALankaGateway-
|
|
6
|
+
import '../ILankaScenarioVM-DUsI-fSc.js';
|
|
7
|
+
import '../ILankaScenarioMetadata-GoWWNEQL.js';
|
|
8
|
+
import '../ALankaGateway-CkW1LbKE.js';
|
|
9
9
|
import '../lankaStandardValidator-CL-r-zEV.js';
|
|
10
10
|
import '@standard-schema/spec';
|
|
11
11
|
import '../ALankaSharedStore-B7uepuuk.js';
|
package/dist/_extend/index.js
CHANGED
|
@@ -2,11 +2,11 @@ import {
|
|
|
2
2
|
LankaGatewayLocator,
|
|
3
3
|
LankaScenarioLocator,
|
|
4
4
|
createLankaScope
|
|
5
|
-
} from "../chunk-
|
|
5
|
+
} from "../chunk-5MAQVBI2.js";
|
|
6
6
|
import {
|
|
7
7
|
LankaScenarioVMRegistry,
|
|
8
8
|
LankaScenariosRegistry
|
|
9
|
-
} from "../chunk-
|
|
9
|
+
} from "../chunk-O5ROO7QF.js";
|
|
10
10
|
import {
|
|
11
11
|
composeLankaRequestMiddleware
|
|
12
12
|
} from "../chunk-YR4MZXMU.js";
|
|
@@ -17,7 +17,7 @@ import {
|
|
|
17
17
|
ALankaLocator,
|
|
18
18
|
LankaSharedStoreLocator,
|
|
19
19
|
LankaSingletonLocator
|
|
20
|
-
} from "../chunk-
|
|
20
|
+
} from "../chunk-UE2C76OR.js";
|
|
21
21
|
import "../chunk-C2HP7CRD.js";
|
|
22
22
|
import "../chunk-D27MREPB.js";
|
|
23
23
|
import "../chunk-BGVDPDX4.js";
|
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
export { I as ILankaRuntime, T as TLankaRuntimeResolver, s as setLankaRuntimeResolver } from '../activeRuntime-
|
|
2
|
-
import '../ILankaScenarioVM-
|
|
3
|
-
import '../LankaScenarioLocator-
|
|
4
|
-
import '../ILankaScenarioMetadata-
|
|
5
|
-
import '../ALankaGateway-
|
|
1
|
+
export { I as ILankaRuntime, T as TLankaRuntimeResolver, s as setLankaRuntimeResolver } from '../activeRuntime-B336NU5I.js';
|
|
2
|
+
import '../ILankaScenarioVM-DUsI-fSc.js';
|
|
3
|
+
import '../LankaScenarioLocator-D86TIwiu.js';
|
|
4
|
+
import '../ILankaScenarioMetadata-GoWWNEQL.js';
|
|
5
|
+
import '../ALankaGateway-CkW1LbKE.js';
|
|
6
6
|
import '../lankaStandardValidator-CL-r-zEV.js';
|
|
7
7
|
import '@standard-schema/spec';
|
|
8
|
-
import '../LankaSharedStoreLocator-
|
|
8
|
+
import '../LankaSharedStoreLocator-zS2kLu-S.js';
|
|
9
9
|
import '../ALankaSharedStore-B7uepuuk.js';
|
|
10
10
|
import 'zustand/vanilla';
|
|
11
11
|
import '../ILankaRuntimeConfig-Vl436GWK.js';
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
import { L as LankaEventBusInstance, I as ILankaScenarioVM } from './ILankaScenarioVM-
|
|
2
|
-
import { c as LankaScenariosRegistry, b as LankaScenarioVMRegistry, L as LankaGatewayLocator, a as LankaScenarioLocator } from './LankaScenarioLocator-
|
|
1
|
+
import { L as LankaEventBusInstance, I as ILankaScenarioVM } from './ILankaScenarioVM-DUsI-fSc.js';
|
|
2
|
+
import { c as LankaScenariosRegistry, b as LankaScenarioVMRegistry, L as LankaGatewayLocator, a as LankaScenarioLocator } from './LankaScenarioLocator-D86TIwiu.js';
|
|
3
3
|
import { b as ILankaRuntimeConfig } from './ILankaRuntimeConfig-Vl436GWK.js';
|
|
4
4
|
import { I as ILankaInFlightCounter } from './lankaHttpInFlight-Bk1eIuSx.js';
|
|
5
5
|
import { T as TLankaRequestMiddleware } from './lankaRequestMiddleware-DAC5kCb7.js';
|
|
6
|
-
import { b as LankaSingletonLocator, L as LankaSharedStoreLocator } from './LankaSharedStoreLocator-
|
|
6
|
+
import { b as LankaSingletonLocator, L as LankaSharedStoreLocator } from './LankaSharedStoreLocator-zS2kLu-S.js';
|
|
7
7
|
|
|
8
8
|
/**
|
|
9
9
|
* The pointer to the framework instance that ambient facades resolve to.
|
|
@@ -1,150 +1,19 @@
|
|
|
1
|
-
import { I as
|
|
2
|
-
|
|
3
|
-
import {
|
|
4
|
-
|
|
5
|
-
import '../
|
|
6
|
-
import '../
|
|
7
|
-
import '
|
|
8
|
-
import '../
|
|
9
|
-
import '../
|
|
10
|
-
import '../ILankaScenarioMetadata-Bu-yggTZ.js';
|
|
11
|
-
import '../ALankaGateway-ExlRGT3D.js';
|
|
1
|
+
import { c as ILankaPlugin, e as ILankaServiceConfig, I as ILankaBootstrapConfig, a as ILankaInstance } from '../createLanka-DI1CSy2Q.js';
|
|
2
|
+
export { b as ILankaInstanceConfig, d as ILankaScenarioBootstrapConfig, f as createLanka } from '../createLanka-DI1CSy2Q.js';
|
|
3
|
+
import { I as ILankaFlags, a as ILankaHost } from '../ILankaRuntimeConfig-Vl436GWK.js';
|
|
4
|
+
export { I as ILankaScope } from '../createLankaScope-BiFxNQgl.js';
|
|
5
|
+
import '../activeRuntime-B336NU5I.js';
|
|
6
|
+
import '../ILankaScenarioVM-DUsI-fSc.js';
|
|
7
|
+
import '../LankaScenarioLocator-D86TIwiu.js';
|
|
8
|
+
import '../ILankaScenarioMetadata-GoWWNEQL.js';
|
|
9
|
+
import '../ALankaGateway-CkW1LbKE.js';
|
|
12
10
|
import '../lankaStandardValidator-CL-r-zEV.js';
|
|
13
11
|
import '@standard-schema/spec';
|
|
12
|
+
import '../LankaSharedStoreLocator-zS2kLu-S.js';
|
|
13
|
+
import '../ALankaSharedStore-B7uepuuk.js';
|
|
14
|
+
import 'zustand/vanilla';
|
|
14
15
|
import '../lankaHttpInFlight-Bk1eIuSx.js';
|
|
15
|
-
|
|
16
|
-
/**
|
|
17
|
-
* A plugin is an extension core knows by SHAPE rather than by name.
|
|
18
|
-
*
|
|
19
|
-
* ## Plugin versus module
|
|
20
|
-
*
|
|
21
|
-
* A module is called by the application (`app → module`) and core does not know
|
|
22
|
-
* it exists. A plugin sits on the path core itself walks (`app → core → plugin`).
|
|
23
|
-
* The test question: does core need a hook for this to work? No — then it is a
|
|
24
|
-
* module, and making it a plugin costs more, because the hook has to be supported
|
|
25
|
-
* forever.
|
|
26
|
-
*
|
|
27
|
-
* ## Why `install` receives the instance
|
|
28
|
-
*
|
|
29
|
-
* So a plugin has no private route to the framework. Everything it can do comes
|
|
30
|
-
* from the instance it was given, which means two instances in one process (a
|
|
31
|
-
* test beside the app) do not share its configuration.
|
|
32
|
-
*/
|
|
33
|
-
interface ILankaPlugin {
|
|
34
|
-
/**
|
|
35
|
-
* The name the plugin is recognised by. Registering the same name twice is
|
|
36
|
-
* rejected: two copies of a retry policy would silently double the request
|
|
37
|
-
* count.
|
|
38
|
-
*/
|
|
39
|
-
readonly name: string;
|
|
40
|
-
/**
|
|
41
|
-
* Installation. The returned function removes everything the plugin installed
|
|
42
|
-
* and is called when the plugin is removed and when the instance is disposed.
|
|
43
|
-
*/
|
|
44
|
-
install: (lanka: ILankaInstance) => (() => void) | void;
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
/**
|
|
48
|
-
* A framework instance: all framework state in one object.
|
|
49
|
-
*
|
|
50
|
-
* What instance-scoped state buys: two apps in one process (micro-frontends,
|
|
51
|
-
* Storybook beside the app) no longer share a bus, locator caches and mock mode;
|
|
52
|
-
* SSR does not reuse state between different users' requests; and test isolation
|
|
53
|
-
* rests on construction rather than on a global `beforeEach` reaching into
|
|
54
|
-
* internal registries.
|
|
55
|
-
*
|
|
56
|
-
* **Ambient facades** — `lankaEventBus.dispatch`, `lankaSingletons.foo`,
|
|
57
|
-
* `getLankaFlags()`, `lankaHttpInFlight` — resolve THE ONE active instance
|
|
58
|
-
* (`internal/activeRuntime.ts`). Isolation belongs to whoever holds an instance;
|
|
59
|
-
* a facade cannot offer it.
|
|
60
|
-
*
|
|
61
|
-
* One thing stays at module level deliberately: `ALankaScenario` collects
|
|
62
|
-
* constructed scenarios into a static pool. That is a REGISTRY OF DEFINITIONS,
|
|
63
|
-
* not runtime state — the classes come from one `@lanka_di/Scenarios` barrel and
|
|
64
|
-
* both instances must see the same list. Splitting it would be divergence.
|
|
65
|
-
*/
|
|
66
|
-
interface ILankaInstance extends ILankaRuntime {
|
|
67
|
-
/**
|
|
68
|
-
* Adds a wrapper around every request. Returns a function that removes it.
|
|
69
|
-
*
|
|
70
|
-
* This is how `@lankajs/plugin-http` installs retry, the idempotency key, the
|
|
71
|
-
* CSRF header and auth refresh.
|
|
72
|
-
*/
|
|
73
|
-
useRequestMiddleware(middleware: TLankaRequestMiddleware): () => void;
|
|
74
|
-
/** Default timeout for every request of this instance. */
|
|
75
|
-
setRequestTimeout(timeoutMs: number | undefined): void;
|
|
76
|
-
/** Resolves a service in the root scope — for the instance's whole lifetime. */
|
|
77
|
-
resolve<TInstance>(propertyName: string): TInstance;
|
|
78
|
-
/**
|
|
79
|
-
* Creates a scope: a lifetime shorter than the application's.
|
|
80
|
-
*
|
|
81
|
-
* An object created in a scope goes away with it.
|
|
82
|
-
*/
|
|
83
|
-
createScope(): ILankaScope;
|
|
84
|
-
/**
|
|
85
|
-
* Registers a plugin. Returns a function that removes it.
|
|
86
|
-
*
|
|
87
|
-
* The fifth and last extension point. An extension point declared before
|
|
88
|
-
* anything plugs into it describes an imagined need while costing real
|
|
89
|
-
* support, so this one arrived with the FIRST plugin.
|
|
90
|
-
*/
|
|
91
|
-
use(plugin: ILankaPlugin): () => void;
|
|
92
|
-
/** Runs services and the scenario layer. Idempotent. */
|
|
93
|
-
bootstrap(config?: ILankaBootstrapConfig): Promise<void>;
|
|
94
|
-
/** Has bootstrap already run? */
|
|
95
|
-
isBootstrapped(): boolean;
|
|
96
|
-
/** Makes this instance the one ambient facades resolve to. */
|
|
97
|
-
activate(): void;
|
|
98
|
-
/**
|
|
99
|
-
* Removes subscriptions, clears registries and, if this instance was active,
|
|
100
|
-
* clears the pointer. Returns the framework to its pre-bootstrap state.
|
|
101
|
-
*/
|
|
102
|
-
dispose(): void;
|
|
103
|
-
}
|
|
104
|
-
interface ILankaInstanceConfig {
|
|
105
|
-
host: ILankaHost;
|
|
106
|
-
flags?: ILankaFlags;
|
|
107
|
-
}
|
|
108
|
-
interface ILankaServiceConfig {
|
|
109
|
-
name?: string;
|
|
110
|
-
init: () => void | Promise<void>;
|
|
111
|
-
sync?: boolean;
|
|
112
|
-
priority?: number;
|
|
113
|
-
/**
|
|
114
|
-
* A failure of this service does not abort bootstrap.
|
|
115
|
-
*
|
|
116
|
-
* Without the flag one failed service takes the WHOLE phase with it: the async
|
|
117
|
-
* phase because of `Promise.all`, the sync phase because later tasks never run.
|
|
118
|
-
* Wrapping the failure in a swallowing `try/catch` is worse still — the app
|
|
119
|
-
* starts with a partially executed plan and does not know it.
|
|
120
|
-
*/
|
|
121
|
-
optional?: boolean;
|
|
122
|
-
/**
|
|
123
|
-
* How long to wait for the service. Overrunning counts as a failure.
|
|
124
|
-
*
|
|
125
|
-
* Without a deadline a service that never settles holds bootstrap forever and
|
|
126
|
-
* the app never paints its first screen. Failing is more honest than waiting:
|
|
127
|
-
* an optional service is skipped, a required one names itself.
|
|
128
|
-
*/
|
|
129
|
-
timeoutMs?: number;
|
|
130
|
-
}
|
|
131
|
-
interface ILankaScenarioBootstrapConfig {
|
|
132
|
-
sync?: boolean;
|
|
133
|
-
priority?: number;
|
|
134
|
-
}
|
|
135
|
-
interface ILankaBootstrapConfig {
|
|
136
|
-
services?: ILankaServiceConfig[];
|
|
137
|
-
scenarios?: ILankaScenarioBootstrapConfig;
|
|
138
|
-
}
|
|
139
|
-
/**
|
|
140
|
-
* Creates an instance and makes it active.
|
|
141
|
-
*
|
|
142
|
-
* Activating on creation is the deliberate default: there is almost always one
|
|
143
|
-
* app and the facades must work immediately. A second instance takes the
|
|
144
|
-
* pointer — the last one created serves the facades. Callers needing another
|
|
145
|
-
* order call `activate()` explicitly.
|
|
146
|
-
*/
|
|
147
|
-
declare function createLanka(config: ILankaInstanceConfig): ILankaInstance;
|
|
16
|
+
import '../lankaRequestMiddleware-DAC5kCb7.js';
|
|
148
17
|
|
|
149
18
|
/** What `startLanka` takes beyond the host, all of it optional. */
|
|
150
19
|
interface ILankaStartOptions {
|
|
@@ -239,4 +108,4 @@ declare abstract class ALankaPlugin implements ILankaPlugin {
|
|
|
239
108
|
install(lanka: ILankaInstance): () => void;
|
|
240
109
|
}
|
|
241
110
|
|
|
242
|
-
export { ALankaPlugin,
|
|
111
|
+
export { ALankaPlugin, ILankaBootstrapConfig, ILankaInstance, ILankaPlugin, ILankaServiceConfig, type ILankaStartOptions, type TLankaStartConfig, resetActiveLanka, startLanka };
|
package/dist/bootstrap/index.js
CHANGED
|
@@ -3,13 +3,13 @@ import {
|
|
|
3
3
|
createLanka,
|
|
4
4
|
resetActiveLanka,
|
|
5
5
|
startLanka
|
|
6
|
-
} from "../chunk-
|
|
7
|
-
import "../chunk-
|
|
8
|
-
import "../chunk-
|
|
9
|
-
import "../chunk-
|
|
6
|
+
} from "../chunk-LMKLLEHA.js";
|
|
7
|
+
import "../chunk-UGXSGQPW.js";
|
|
8
|
+
import "../chunk-5MAQVBI2.js";
|
|
9
|
+
import "../chunk-O5ROO7QF.js";
|
|
10
10
|
import "../chunk-XESL274R.js";
|
|
11
11
|
import "../chunk-UJEC7H6K.js";
|
|
12
|
-
import "../chunk-
|
|
12
|
+
import "../chunk-UE2C76OR.js";
|
|
13
13
|
import "../chunk-C2HP7CRD.js";
|
|
14
14
|
import "../chunk-D27MREPB.js";
|
|
15
15
|
import "../chunk-BGVDPDX4.js";
|