Middleware
The structure of a middleware function
Here is the most basic middleware (mdw) function in starfx
:
1function* (ctx, next) {
2 yield* next();
3}
Thunks and endpoints are just thin wrappers around a mdw stack:
For example, the recommended mdw stack for createApi()
looks like this:
1import { createApi, mdw } from "starfx";
2import { schema } from "./schema";
3
4// this api:
5const api = createApi();
6api.use(mdw.api({ schema }));
7api.use(api.routes());
8api.use(mdw.fetch({ baseUrl: "https://api.com" }));
9
10// looks like this:
11[
12 mdw.err,
13 mdw.queryCtx,
14 mdw.customKey,
15 mdw.nameParser,
16 mdw.actions,
17 mdw.loaderApi({ schema }),
18 mdw.cache({ schema }),
19 api.routes(),
20 mdw.composeUrl("https://api.com"),
21 mdw.payload,
22 mdw.request,
23 mdw.json,
24];
When a mdw function calls yield* next()
, all it does it call the next mdw in
the stack. When that yield point resolves, it means all the mdw functions after
it have been called. This doesn't necessarily mean all mdw in the stack will be
called, because like koa
, you can return early inside a mdw function,
essentially cancelling all subsequent mdw.
Context #
The context object is just a plain javascript object that gets passed to every
mdw. The type of ctx
depends ... on the context. But for thunks, we have this
basic structure:
1interface Payload<P> {
2 payload: P;
3}
4
5interface ThunkCtx<P = any> extends Payload<P> {
6 name: string;
7 key: string;
8 action: ActionWithPayload<CreateActionPayload<P>>;
9 actionFn: IfAny<
10 P,
11 CreateAction<ThunkCtx>,
12 CreateActionWithPayload<ThunkCtx<P>, P>
13 >;
14 result: Result<void>;
15}
There are three very important properties that you should know about:
name
- the name you provided when creating the thunkpayload
- the arbitrary data you passed into the thunkkey
- a hash ofname
andpayload