@ozanarslan/corpus 0.0.1
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/LICENSE.txt +20 -0
- package/README.md +337 -0
- package/dist/App/index.d.ts +377 -0
- package/dist/App/index.d.ts.map +1 -0
- package/dist/C.namespace.d.ts +27 -0
- package/dist/C.namespace.d.ts.map +1 -0
- package/dist/Config/index.d.ts +163 -0
- package/dist/Config/index.d.ts.map +1 -0
- package/dist/Context/ContextAccess/index.d.ts +50 -0
- package/dist/Context/ContextAccess/index.d.ts.map +1 -0
- package/dist/Context/index.d.ts +162 -0
- package/dist/Context/index.d.ts.map +1 -0
- package/dist/Controller/index.d.ts +164 -0
- package/dist/Controller/index.d.ts.map +1 -0
- package/dist/Cookies/index.d.ts +81 -0
- package/dist/Cookies/index.d.ts.map +1 -0
- package/dist/Cors/index.d.ts +135 -0
- package/dist/Cors/index.d.ts.map +1 -0
- package/dist/Exception/index.d.ts +85 -0
- package/dist/Exception/index.d.ts.map +1 -0
- package/dist/Globals/AppsRegistry/index.d.ts +48 -0
- package/dist/Globals/AppsRegistry/index.d.ts.map +1 -0
- package/dist/Globals/ParsersRegistry/index.d.ts +93 -0
- package/dist/Globals/ParsersRegistry/index.d.ts.map +1 -0
- package/dist/Globals/index.d.ts +109 -0
- package/dist/Globals/index.d.ts.map +1 -0
- package/dist/Headers/index.d.ts +208 -0
- package/dist/Headers/index.d.ts.map +1 -0
- package/dist/Middleware/index.d.ts +125 -0
- package/dist/Middleware/index.d.ts.map +1 -0
- package/dist/ParserBase/BodyParser/index.d.ts +138 -0
- package/dist/ParserBase/BodyParser/index.d.ts.map +1 -0
- package/dist/ParserBase/FormDataParser/index.d.ts +57 -0
- package/dist/ParserBase/FormDataParser/index.d.ts.map +1 -0
- package/dist/ParserBase/SchemaParser/index.d.ts +143 -0
- package/dist/ParserBase/SchemaParser/index.d.ts.map +1 -0
- package/dist/ParserBase/SearchParamsParser/index.d.ts +61 -0
- package/dist/ParserBase/SearchParamsParser/index.d.ts.map +1 -0
- package/dist/ParserBase/URLParamsParser/index.d.ts +32 -0
- package/dist/ParserBase/URLParamsParser/index.d.ts.map +1 -0
- package/dist/ParserBase/index.d.ts +92 -0
- package/dist/ParserBase/index.d.ts.map +1 -0
- package/dist/RateLimiter/index.d.ts +321 -0
- package/dist/RateLimiter/index.d.ts.map +1 -0
- package/dist/Request/index.d.ts +81 -0
- package/dist/Request/index.d.ts.map +1 -0
- package/dist/Res/index.d.ts +353 -0
- package/dist/Res/index.d.ts.map +1 -0
- package/dist/RouteBase/BundleRoute/index.d.ts +268 -0
- package/dist/RouteBase/BundleRoute/index.d.ts.map +1 -0
- package/dist/RouteBase/FileRoute/index.d.ts +121 -0
- package/dist/RouteBase/FileRoute/index.d.ts.map +1 -0
- package/dist/RouteBase/Route/index.d.ts +83 -0
- package/dist/RouteBase/Route/index.d.ts.map +1 -0
- package/dist/RouteBase/StaticRoute/index.d.ts +149 -0
- package/dist/RouteBase/StaticRoute/index.d.ts.map +1 -0
- package/dist/RouteBase/WebSocketRoute/index.d.ts +117 -0
- package/dist/RouteBase/WebSocketRoute/index.d.ts.map +1 -0
- package/dist/RouteBase/index.d.ts +206 -0
- package/dist/RouteBase/index.d.ts.map +1 -0
- package/dist/Server/index.d.ts +44 -0
- package/dist/Server/index.d.ts.map +1 -0
- package/dist/XFile/index.d.ts +202 -0
- package/dist/XFile/index.d.ts.map +1 -0
- package/dist/exports.d.ts +11 -0
- package/dist/exports.d.ts.map +1 -0
- package/dist/index.d.ts +5 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +12 -0
- package/dist/index.js.map +47 -0
- package/dist/initialize.d.ts +22 -0
- package/dist/initialize.d.ts.map +1 -0
- package/dist/utils/assert.d.ts +7 -0
- package/dist/utils/assert.d.ts.map +1 -0
- package/dist/utils/is.d.ts +17 -0
- package/dist/utils/is.d.ts.map +1 -0
- package/dist/utils/lazy.d.ts +27 -0
- package/dist/utils/lazy.d.ts.map +1 -0
- package/dist/utils/logger.d.ts +31 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/object.d.ts +20 -0
- package/dist/utils/object.d.ts.map +1 -0
- package/dist/utils/path.d.ts +6 -0
- package/dist/utils/path.d.ts.map +1 -0
- package/dist/utils/tuple.d.ts +3 -0
- package/dist/utils/tuple.d.ts.map +1 -0
- package/package.json +57 -0
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Process-wide registry of every {@link AppInterface} instance that has been
|
|
3
|
+
* constructed.
|
|
4
|
+
*
|
|
5
|
+
* The registry is what lets {@link RouteBase} implementations and
|
|
6
|
+
* {@link Middleware} attach themselves without being handed an app: they call
|
|
7
|
+
* {@link getNearestApp} and find the most recently constructed one. The array
|
|
8
|
+
* lives on {@link Globals}, so it survives module re-evaluation and is shared
|
|
9
|
+
* across the whole process.
|
|
10
|
+
*
|
|
11
|
+
* @module AppsRegistry
|
|
12
|
+
*/
|
|
13
|
+
import type { AppInterface } from "../../App";
|
|
14
|
+
/**
|
|
15
|
+
* The registry itself: every {@link AppInterface} in construction order, oldest
|
|
16
|
+
* first. The last entry is the one {@link getNearestApp} resolves to.
|
|
17
|
+
*/
|
|
18
|
+
type AppsRegistry = Array<AppInterface>;
|
|
19
|
+
/**
|
|
20
|
+
* Reads the registry from {@link Globals}, creating an empty one on first
|
|
21
|
+
* access.
|
|
22
|
+
*
|
|
23
|
+
* @returns The shared {@link AppsRegistry}. The array is live — mutating it
|
|
24
|
+
* mutates the registry.
|
|
25
|
+
*/
|
|
26
|
+
declare function getOrInitAppsRegistry(): AppsRegistry;
|
|
27
|
+
/**
|
|
28
|
+
* Resolves the {@link AppInterface} that newly constructed routes and
|
|
29
|
+
* middlewares should attach to: the most recently registered one.
|
|
30
|
+
*
|
|
31
|
+
* With a single app — the common case — this is simply that app. With several,
|
|
32
|
+
* "nearest" means last constructed, so an app must be instantiated before the
|
|
33
|
+
* routes belonging to it.
|
|
34
|
+
*
|
|
35
|
+
* @returns The most recently registered {@link AppInterface}.
|
|
36
|
+
* @throws {@link Error} when no app has been constructed yet.
|
|
37
|
+
*/
|
|
38
|
+
declare function getNearestApp(): AppInterface;
|
|
39
|
+
/**
|
|
40
|
+
* Appends an app to the registry, making it the one {@link getNearestApp}
|
|
41
|
+
* returns. Called by the {@link App} constructor; there is no reason to call it
|
|
42
|
+
* by hand.
|
|
43
|
+
*
|
|
44
|
+
* @param app - The {@link AppInterface} to register.
|
|
45
|
+
*/
|
|
46
|
+
declare function registerApp(app: AppInterface): void;
|
|
47
|
+
export { type AppsRegistry, getOrInitAppsRegistry, getNearestApp, registerApp };
|
|
48
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/Globals/AppsRegistry/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,OAAO,CAAC;AAI1C;;;GAGG;AACH,KAAK,YAAY,GAAG,KAAK,CAAC,YAAY,CAAC,CAAC;AAExC;;;;;;GAMG;AACH,iBAAS,qBAAqB,IAAI,YAAY,CAM7C;AAED;;;;;;;;;;GAUG;AACH,iBAAS,aAAa,IAAI,YAAY,CAKrC;AAED;;;;;;GAMG;AACH,iBAAS,WAAW,CAAC,GAAG,EAAE,YAAY,GAAG,IAAI,CAG5C;AAED,OAAO,EAAE,KAAK,YAAY,EAAE,qBAAqB,EAAE,aAAa,EAAE,WAAW,EAAE,CAAC"}
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The single place every parsing decision in the framework is resolved from —
|
|
3
|
+
* and the single place to replace them.
|
|
4
|
+
*
|
|
5
|
+
* Nothing in corpus constructs a parser inline. {@link App} resolves the
|
|
6
|
+
* registry while compiling routes, and {@link BodyParser} reaches back into it
|
|
7
|
+
* for {@link FormDataParser} and {@link SearchParamsParser} rather than owning
|
|
8
|
+
* instances of its own. Replacing an entry therefore changes how the whole
|
|
9
|
+
* framework parses that surface, across every {@link RouteBase} on every
|
|
10
|
+
* {@link App}, without touching a single route definition.
|
|
11
|
+
*
|
|
12
|
+
* Every slot is plug and play. Each is typed as an interface
|
|
13
|
+
* ({@link ParserBaseInterface}, {@link BodyParserInterface},
|
|
14
|
+
* {@link SchemaParserInterface}), never as a concrete class, so a replacement
|
|
15
|
+
* only has to satisfy the contract — subclassing the default is optional.
|
|
16
|
+
*
|
|
17
|
+
* ```ts
|
|
18
|
+
* // Replace one parser; the rest keep their defaults.
|
|
19
|
+
* setParsersRegistry({ bodyParser: new MyBodyParser() });
|
|
20
|
+
*
|
|
21
|
+
* await app.listen();
|
|
22
|
+
* ```
|
|
23
|
+
*
|
|
24
|
+
* Overrides must be in place before {@link App.listen}: routes read the registry
|
|
25
|
+
* as they are compiled, so anything swapped in afterwards is never reached.
|
|
26
|
+
*
|
|
27
|
+
* The registry lives on {@link Globals}, so it is created once per process and
|
|
28
|
+
* shared by every {@link App}.
|
|
29
|
+
*
|
|
30
|
+
* @module ParsersRegistry
|
|
31
|
+
*/
|
|
32
|
+
import type { ParserBaseInterface } from "../../ParserBase";
|
|
33
|
+
import { type BodyParserInterface } from "../../ParserBase/BodyParser";
|
|
34
|
+
import { type SchemaParserInterface } from "../../ParserBase/SchemaParser";
|
|
35
|
+
/**
|
|
36
|
+
* The set of parsers the framework resolves at request time. Every field is an
|
|
37
|
+
* interface, so each one can be replaced independently through
|
|
38
|
+
* {@link setParsersRegistry}.
|
|
39
|
+
*/
|
|
40
|
+
interface ParsersRegistry {
|
|
41
|
+
/**
|
|
42
|
+
* Turns the raw path parameters matched by a {@link RouteBase} into
|
|
43
|
+
* {@link Context.params}. Defaults to {@link URLParamsParser}.
|
|
44
|
+
*/
|
|
45
|
+
urlParamsParser: ParserBaseInterface<Record<string, string>>;
|
|
46
|
+
/**
|
|
47
|
+
* Turns a query string into {@link Context.search}. Defaults to
|
|
48
|
+
* {@link SearchParamsParser}, which {@link BodyParser} also reuses for
|
|
49
|
+
* `application/x-www-form-urlencoded` bodies.
|
|
50
|
+
*/
|
|
51
|
+
searchParamsParser: ParserBaseInterface<URLSearchParams>;
|
|
52
|
+
/**
|
|
53
|
+
* Turns `multipart/form-data` into an object. Defaults to
|
|
54
|
+
* {@link FormDataParser} and is reached through {@link BodyParser} rather than
|
|
55
|
+
* called directly.
|
|
56
|
+
*/
|
|
57
|
+
formDataParser: ParserBaseInterface<FormData>;
|
|
58
|
+
/**
|
|
59
|
+
* Reads and decodes request and response bodies by content type. Defaults to
|
|
60
|
+
* {@link BodyParser}.
|
|
61
|
+
*/
|
|
62
|
+
bodyParser: BodyParserInterface;
|
|
63
|
+
/**
|
|
64
|
+
* Validates already-parsed params, search and body against the schemas
|
|
65
|
+
* declared in a route's {@link Config}. Defaults to {@link SchemaParser},
|
|
66
|
+
* which supports Zod and ArkType.
|
|
67
|
+
*/
|
|
68
|
+
schemaParser: SchemaParserInterface;
|
|
69
|
+
}
|
|
70
|
+
/**
|
|
71
|
+
* Reads the registry from {@link Globals}, constructing the defaults on first
|
|
72
|
+
* access.
|
|
73
|
+
*
|
|
74
|
+
* Called by {@link App} during route compilation and by {@link BodyParser} when
|
|
75
|
+
* it needs a sibling parser.
|
|
76
|
+
*
|
|
77
|
+
* @returns The shared {@link ParsersRegistry}.
|
|
78
|
+
*/
|
|
79
|
+
declare function getOrInitParsersRegistry(): ParsersRegistry;
|
|
80
|
+
/**
|
|
81
|
+
* Overrides one or more parsers. Only the provided keys are replaced;
|
|
82
|
+
* unspecified parsers keep their current implementation.
|
|
83
|
+
*
|
|
84
|
+
* Must be called before {@link App.listen} — routes resolve their parsers as
|
|
85
|
+
* they are compiled, so a later override has no effect on an already-listening
|
|
86
|
+
* app.
|
|
87
|
+
*
|
|
88
|
+
* @param overrides - The {@link ParsersRegistry} entries to swap in. Each value
|
|
89
|
+
* need only satisfy its interface; it does not have to extend the default class.
|
|
90
|
+
*/
|
|
91
|
+
declare function setParsersRegistry(overrides: Partial<ParsersRegistry>): void;
|
|
92
|
+
export { type ParsersRegistry, getOrInitParsersRegistry, setParsersRegistry };
|
|
93
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/Globals/ParsersRegistry/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AAGH,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,cAAc,CAAC;AACxD,OAAO,EAAE,KAAK,mBAAmB,EAAc,MAAM,yBAAyB,CAAC;AAE/E,OAAO,EAAE,KAAK,qBAAqB,EAAgB,MAAM,2BAA2B,CAAC;AAIrF;;;;GAIG;AACH,UAAU,eAAe;IACxB;;;OAGG;IACH,eAAe,EAAE,mBAAmB,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC;IAC7D;;;;OAIG;IACH,kBAAkB,EAAE,mBAAmB,CAAC,eAAe,CAAC,CAAC;IACzD;;;;OAIG;IACH,cAAc,EAAE,mBAAmB,CAAC,QAAQ,CAAC,CAAC;IAC9C;;;OAGG;IACH,UAAU,EAAE,mBAAmB,CAAC;IAChC;;;;OAIG;IACH,YAAY,EAAE,qBAAqB,CAAC;CACpC;AAED;;;;;;;;GAQG;AACH,iBAAS,wBAAwB,IAAI,eAAe,CAanD;AAED;;;;;;;;;;GAUG;AACH,iBAAS,kBAAkB,CAAC,SAAS,EAAE,OAAO,CAAC,eAAe,CAAC,GAAG,IAAI,CAErE;AAED,OAAO,EAAE,KAAK,eAAe,EAAE,wBAAwB,EAAE,kBAAkB,EAAE,CAAC"}
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Typed process-wide state, stored on `globalThis` under package-namespaced
|
|
3
|
+
* symbols.
|
|
4
|
+
*
|
|
5
|
+
* Two things in the framework must be singletons regardless of how many times
|
|
6
|
+
* the module is evaluated: the {@link AppsRegistry} that {@link getNearestApp}
|
|
7
|
+
* resolves against, and the {@link ParsersRegistry} that every route reads while
|
|
8
|
+
* compiling. Module-level variables cannot guarantee that — a duplicated
|
|
9
|
+
* dependency, a re-import under a different resolution, or a test runner
|
|
10
|
+
* reloading modules each produces a second copy, and two apps registries means
|
|
11
|
+
* routes registering onto an app that is never served.
|
|
12
|
+
*
|
|
13
|
+
* The keys are `Symbol.for("@ozanarslan/corpus:<key>")`, so they are shared
|
|
14
|
+
* across every copy of the package in the process and cannot collide with
|
|
15
|
+
* another library's globals.
|
|
16
|
+
*
|
|
17
|
+
* @module Globals
|
|
18
|
+
*/
|
|
19
|
+
import type { AppsRegistry } from "./AppsRegistry";
|
|
20
|
+
import type { ParsersRegistry } from "./ParsersRegistry";
|
|
21
|
+
/**
|
|
22
|
+
* What lives in the global store, and the type of each entry. Adding a key here
|
|
23
|
+
* requires a matching entry in {@link GLOBAL_SYMBOLS}, which the `satisfies`
|
|
24
|
+
* clause enforces.
|
|
25
|
+
*/
|
|
26
|
+
interface GlobalRegistry {
|
|
27
|
+
/** Whether one-time framework setup has run. */
|
|
28
|
+
initialized: boolean;
|
|
29
|
+
/** The shared {@link AppsRegistry} — every {@link App} constructed in this process. */
|
|
30
|
+
apps: AppsRegistry;
|
|
31
|
+
/** The shared {@link ParsersRegistry} — the parsers routes resolve at compile time. */
|
|
32
|
+
parsers: ParsersRegistry;
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* The symbol for each {@link GlobalRegistry} entry.
|
|
36
|
+
*
|
|
37
|
+
* Registered through `Symbol.for`, so every copy of the package in the process
|
|
38
|
+
* resolves to the same symbol and therefore to the same stored value.
|
|
39
|
+
*/
|
|
40
|
+
declare const GLOBAL_SYMBOLS: {
|
|
41
|
+
readonly initialized: symbol;
|
|
42
|
+
readonly apps: symbol;
|
|
43
|
+
readonly parsers: symbol;
|
|
44
|
+
};
|
|
45
|
+
/**
|
|
46
|
+
* Typed accessor for the global store.
|
|
47
|
+
*
|
|
48
|
+
* Keys are constrained to {@link GlobalRegistry}, so every read and write is
|
|
49
|
+
* checked against the type declared for that entry.
|
|
50
|
+
*/
|
|
51
|
+
declare class Globals {
|
|
52
|
+
/** The backing store: `globalThis`, typed for symbol access. */
|
|
53
|
+
private static readonly store;
|
|
54
|
+
/**
|
|
55
|
+
* Returns the symbol an entry is stored under.
|
|
56
|
+
*
|
|
57
|
+
* Useful for inspecting or clearing global state directly — in a test that
|
|
58
|
+
* needs a clean process, for instance.
|
|
59
|
+
*
|
|
60
|
+
* @param key - The {@link GlobalRegistry} entry.
|
|
61
|
+
* @returns Its symbol from {@link GLOBAL_SYMBOLS}.
|
|
62
|
+
*/
|
|
63
|
+
static getSymbol<K extends keyof GlobalRegistry>(key: K): (typeof GLOBAL_SYMBOLS)[K];
|
|
64
|
+
/**
|
|
65
|
+
* Reads an entry, creating it on first access.
|
|
66
|
+
*
|
|
67
|
+
* The initialiser runs only when the entry is absent, which is what makes this
|
|
68
|
+
* safe to call from anywhere: the first caller creates the value and every
|
|
69
|
+
* later one gets that same instance. This is how
|
|
70
|
+
* {@link getOrInitAppsRegistry} and {@link getOrInitParsersRegistry} work.
|
|
71
|
+
*
|
|
72
|
+
* @param key - The {@link GlobalRegistry} entry.
|
|
73
|
+
* @param init - Builds the initial value. Not called if the entry exists.
|
|
74
|
+
* @returns The stored value.
|
|
75
|
+
*/
|
|
76
|
+
static create<K extends keyof GlobalRegistry>(key: K, init: () => GlobalRegistry[K]): GlobalRegistry[K];
|
|
77
|
+
/**
|
|
78
|
+
* Reads an entry that is expected to exist.
|
|
79
|
+
*
|
|
80
|
+
* @param key - The {@link GlobalRegistry} entry.
|
|
81
|
+
* @returns The stored value.
|
|
82
|
+
* @throws {@link Error} when the entry has not been created. Use
|
|
83
|
+
* {@link Globals.create} when the caller may be the first.
|
|
84
|
+
*/
|
|
85
|
+
static get<K extends keyof GlobalRegistry>(key: K): GlobalRegistry[K];
|
|
86
|
+
/**
|
|
87
|
+
* Writes an entry, replacing any existing value.
|
|
88
|
+
*
|
|
89
|
+
* @param key - The {@link GlobalRegistry} entry.
|
|
90
|
+
* @param value - The value to store.
|
|
91
|
+
*/
|
|
92
|
+
static set<K extends keyof GlobalRegistry>(key: K, value: GlobalRegistry[K]): void;
|
|
93
|
+
/**
|
|
94
|
+
* Reports whether an entry has been created, without creating it or throwing.
|
|
95
|
+
*
|
|
96
|
+
* @param key - The {@link GlobalRegistry} entry.
|
|
97
|
+
* @returns `true` when the entry exists.
|
|
98
|
+
*/
|
|
99
|
+
static has<K extends keyof GlobalRegistry>(key: K): boolean;
|
|
100
|
+
/**
|
|
101
|
+
* Removes an entry, so the next {@link Globals.create} rebuilds it from
|
|
102
|
+
* scratch. Mainly useful for resetting state between tests.
|
|
103
|
+
*
|
|
104
|
+
* @param key - The {@link GlobalRegistry} entry.
|
|
105
|
+
*/
|
|
106
|
+
static delete<K extends keyof GlobalRegistry>(key: K): void;
|
|
107
|
+
}
|
|
108
|
+
export { type GlobalRegistry, Globals, GLOBAL_SYMBOLS };
|
|
109
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/Globals/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAEH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,wBAAwB,CAAC;AAC3D,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAKjE;;;;GAIG;AACH,UAAU,cAAc;IAEvB,gDAAgD;IAChD,WAAW,EAAE,OAAO,CAAC;IACrB,uFAAuF;IACvF,IAAI,EAAE,YAAY,CAAC;IACnB,uFAAuF;IACvF,OAAO,EAAE,eAAe,CAAC;CACzB;AAWD;;;;;GAKG;AACH,QAAA,MAAM,cAAc;;;;CAIqC,CAAC;AAE1D;;;;;GAKG;AACH,cAAM,OAAO;IACZ,gEAAgE;IAChE,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAyC;IAEtE;;;;;;;;OAQG;IACH,MAAM,CAAC,SAAS,CAAC,CAAC,SAAS,MAAM,cAAc,EAAE,GAAG,EAAE,CAAC,GAAG,CAAC,OAAO,cAAc,CAAC,CAAC,CAAC,CAAC;IAIpF;;;;;;;;;;;OAWG;IACH,MAAM,CAAC,MAAM,CAAC,CAAC,SAAS,MAAM,cAAc,EAC3C,GAAG,EAAE,CAAC,EACN,IAAI,EAAE,MAAM,cAAc,CAAC,CAAC,CAAC,GAC3B,cAAc,CAAC,CAAC,CAAC;IAMpB;;;;;;;OAOG;IACH,MAAM,CAAC,GAAG,CAAC,CAAC,SAAS,MAAM,cAAc,EAAE,GAAG,EAAE,CAAC,GAAG,cAAc,CAAC,CAAC,CAAC;IAOrE;;;;;OAKG;IACH,MAAM,CAAC,GAAG,CAAC,CAAC,SAAS,MAAM,cAAc,EAAE,GAAG,EAAE,CAAC,EAAE,KAAK,EAAE,cAAc,CAAC,CAAC,CAAC,GAAG,IAAI;IAKlF;;;;;OAKG;IACH,MAAM,CAAC,GAAG,CAAC,CAAC,SAAS,MAAM,cAAc,EAAE,GAAG,EAAE,CAAC,GAAG,OAAO;IAK3D;;;;;OAKG;IACH,MAAM,CAAC,MAAM,CAAC,CAAC,SAAS,MAAM,cAAc,EAAE,GAAG,EAAE,CAAC,GAAG,IAAI;CAI3D;AAED,OAAO,EAAE,KAAK,cAAc,EAAE,OAAO,EAAE,cAAc,EAAE,CAAC"}
|
|
@@ -0,0 +1,208 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Header names, header-value builders, and the `Headers` extensions the
|
|
3
|
+
* framework relies on.
|
|
4
|
+
*
|
|
5
|
+
* Two things happen here. {@link HeaderKey} gives the common header names as
|
|
6
|
+
* documented constants, so header access is autocompleted and typo-free rather
|
|
7
|
+
* than stringly typed. {@link patchGlobalHeaders} then extends the global
|
|
8
|
+
* `Headers` class with conveniences the native API lacks: non-string values,
|
|
9
|
+
* bulk assignment through {@link Headers.setMany}, and structured builders for
|
|
10
|
+
* `Cache-Control` and `Content-Disposition`.
|
|
11
|
+
*
|
|
12
|
+
* The patch is what lets {@link Res}, {@link FileRoute} and {@link BundleRoute}
|
|
13
|
+
* write headers without stringifying every value by hand. It applies to the
|
|
14
|
+
* process's own `Headers`, so it must be installed once at startup, before any
|
|
15
|
+
* request is served.
|
|
16
|
+
*
|
|
17
|
+
* @module Headers
|
|
18
|
+
*/
|
|
19
|
+
import type { MaybeArray, Nullable, Optional, OrString } from "../utils/is";
|
|
20
|
+
import type { ValueOf } from "../utils/object";
|
|
21
|
+
/**
|
|
22
|
+
* A value accepted by the patched header setters. Numbers and booleans are
|
|
23
|
+
* stringified on the way in, so a byte length or a flag can be passed as-is.
|
|
24
|
+
*/
|
|
25
|
+
type HeadersInitValue = string | number | boolean;
|
|
26
|
+
/**
|
|
27
|
+
* What {@link Headers.setMany} accepts: entry pairs, a plain object, or another
|
|
28
|
+
* `Headers` instance.
|
|
29
|
+
*/
|
|
30
|
+
type CustomHeadersInit = [string, HeadersInitValue][] | Record<string, HeadersInitValue> | Headers;
|
|
31
|
+
/** Just some common headers. See [MDN Reference](https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers) for the full spec. */
|
|
32
|
+
declare const HeaderKey: {
|
|
33
|
+
/** Controls caching mechanisms for requests and responses. */
|
|
34
|
+
readonly CacheControl: "Cache-Control";
|
|
35
|
+
/** Specifies the media type of the resource or data. */
|
|
36
|
+
readonly ContentType: "Content-Type";
|
|
37
|
+
/** Indicates the size of the entity-body in bytes. */
|
|
38
|
+
readonly ContentLength: "Content-Length";
|
|
39
|
+
/** Whether to display payload inline within the page or prompt the user to download it as an attachment. */
|
|
40
|
+
readonly ContentDisposition: "Content-Disposition";
|
|
41
|
+
/** Specifies the character encodings that are acceptable. */
|
|
42
|
+
readonly AcceptEncoding: "Accept-Encoding";
|
|
43
|
+
/** Informs the server about the types of data that can be sent back. */
|
|
44
|
+
readonly Accept: "Accept";
|
|
45
|
+
/** Contains the credentials to authenticate with the server. */
|
|
46
|
+
readonly Authorization: "Authorization";
|
|
47
|
+
/** The user agent string of the client software. */
|
|
48
|
+
readonly UserAgent: "User-Agent";
|
|
49
|
+
/** The domain name of the server and port number. */
|
|
50
|
+
readonly Host: "Host";
|
|
51
|
+
/** The address of the previous web page from which the current request originated. */
|
|
52
|
+
readonly Referer: "Referer";
|
|
53
|
+
/** Indicates whether the connection should be kept alive. */
|
|
54
|
+
readonly Connection: "Connection";
|
|
55
|
+
/** Requests that the server switch to a different protocol (e.g. WebSocket). */
|
|
56
|
+
readonly Upgrade: "Upgrade";
|
|
57
|
+
/** Used to specify directives that must be obeyed by caching mechanisms. */
|
|
58
|
+
readonly Pragma: "Pragma";
|
|
59
|
+
/** The date and time at which the message was sent. */
|
|
60
|
+
readonly Date: "Date";
|
|
61
|
+
/** Makes the request conditional based on the ETag of the resource. */
|
|
62
|
+
readonly IfNoneMatch: "If-None-Match";
|
|
63
|
+
/** Makes the request conditional based on the last modification date. */
|
|
64
|
+
readonly IfModifiedSince: "If-Modified-Since";
|
|
65
|
+
/** An identifier for a specific version of a resource. */
|
|
66
|
+
readonly ETag: "ETag";
|
|
67
|
+
/** The date and time after which the response is considered stale. */
|
|
68
|
+
readonly Expires: "Expires";
|
|
69
|
+
/** The last modification date of the resource. */
|
|
70
|
+
readonly LastModified: "Last-Modified";
|
|
71
|
+
/** Indicates the URL to redirect a page to. */
|
|
72
|
+
readonly Location: "Location";
|
|
73
|
+
/** Defines the authentication method that should be used. */
|
|
74
|
+
readonly WWWAuthenticate: "WWW-Authenticate";
|
|
75
|
+
/** Determines how long the results of a preflight request can be cached. */
|
|
76
|
+
readonly AccessControlMaxAge: "Access-Control-Max-Age";
|
|
77
|
+
/** Indicates whether the response can be shared with resources with credentials. */
|
|
78
|
+
readonly AccessControlAllowCredentials: "Access-Control-Allow-Credentials";
|
|
79
|
+
/** Indicates which HTTP method will be used in the actual CORS request. */
|
|
80
|
+
readonly AccessControlRequestMethod: "Access-Control-Request-Method";
|
|
81
|
+
/** Indicates which headers can be exposed to the browser in a CORS response. */
|
|
82
|
+
readonly AccessControlExposeHeaders: "Access-Control-Expose-Headers";
|
|
83
|
+
/** Indicates which origins are allowed to access the resource. */
|
|
84
|
+
readonly AccessControlAllowOrigin: "Access-Control-Allow-Origin";
|
|
85
|
+
/** Specifies the HTTP methods allowed when accessing the resource in a CORS request. */
|
|
86
|
+
readonly AccessControlAllowMethods: "Access-Control-Allow-Methods";
|
|
87
|
+
/** Specifies the HTTP headers allowed in a CORS request. */
|
|
88
|
+
readonly AccessControlAllowHeaders: "Access-Control-Allow-Headers";
|
|
89
|
+
/** Sends cookies from the server to the client. */
|
|
90
|
+
readonly SetCookie: "Set-Cookie";
|
|
91
|
+
/** Sends cookies from the client to the server. */
|
|
92
|
+
readonly Cookie: "Cookie";
|
|
93
|
+
/** Determines which headers should be used to select a response from cache when content negotiation is in use. */
|
|
94
|
+
readonly Vary: "Vary";
|
|
95
|
+
/** Set to "nosniff" by default in {@link Res}. */
|
|
96
|
+
readonly XContentTypeOptions: "X-Content-Type-Options";
|
|
97
|
+
};
|
|
98
|
+
/**
|
|
99
|
+
* A header name. The {@link HeaderKey} constants are suggested, but
|
|
100
|
+
* {@link OrString} keeps any custom header name assignable — the enum is a
|
|
101
|
+
* convenience, not a restriction.
|
|
102
|
+
*/
|
|
103
|
+
type HeaderKey = OrString<ValueOf<typeof HeaderKey>>;
|
|
104
|
+
/**
|
|
105
|
+
* A caching policy, rendered into a `Cache-Control` value by
|
|
106
|
+
* {@link createCacheControlHeader}. Used by {@link FileRoute.cache} and by each
|
|
107
|
+
* entry of a {@link BundleRouteDefinition}.
|
|
108
|
+
*/
|
|
109
|
+
interface CacheControlDefinition {
|
|
110
|
+
/** Allows shared caches — proxies and CDNs — to store the response, not just the browser. */
|
|
111
|
+
public?: boolean;
|
|
112
|
+
/** How long the response stays fresh, in seconds. */
|
|
113
|
+
maxAge?: number;
|
|
114
|
+
/** Promises the response will never change, so the browser skips revalidation entirely. Only meaningful with a content hash in the URL. */
|
|
115
|
+
immutable?: boolean;
|
|
116
|
+
/** Caches the response but revalidates before every use. Overrides the other directives except `noStore`. */
|
|
117
|
+
noCache?: boolean;
|
|
118
|
+
/** Forbids storing the response anywhere. Overrides every other directive. */
|
|
119
|
+
noStore?: boolean;
|
|
120
|
+
}
|
|
121
|
+
/**
|
|
122
|
+
* Renders a {@link CacheControlDefinition} into a `Cache-Control` header value.
|
|
123
|
+
*
|
|
124
|
+
* The two prohibitive directives take precedence and are emitted alone, since
|
|
125
|
+
* combining them with freshness directives is contradictory: `noStore` wins over
|
|
126
|
+
* everything, then `noCache`. Otherwise the remaining directives are joined in
|
|
127
|
+
* order.
|
|
128
|
+
*
|
|
129
|
+
* @param def - The caching policy to render.
|
|
130
|
+
* @returns The header value, or an empty string when the definition sets
|
|
131
|
+
* nothing.
|
|
132
|
+
*/
|
|
133
|
+
declare function createCacheControlHeader(def: CacheControlDefinition): string;
|
|
134
|
+
/**
|
|
135
|
+
* How a response body should be presented, rendered by
|
|
136
|
+
* {@link createContentDispositionHeader}.
|
|
137
|
+
*/
|
|
138
|
+
interface ContentDispositionDefinition {
|
|
139
|
+
/** `"inline"` to display in the browser, `"attachment"` to prompt a download. */
|
|
140
|
+
disposition: "attachment" | "inline";
|
|
141
|
+
/** The name to save the file under. Omit it to let the client decide. */
|
|
142
|
+
filename?: string;
|
|
143
|
+
}
|
|
144
|
+
/**
|
|
145
|
+
* Renders a {@link ContentDispositionDefinition} into a `Content-Disposition`
|
|
146
|
+
* header value.
|
|
147
|
+
*
|
|
148
|
+
* @param def - The disposition to render.
|
|
149
|
+
* @returns The header value, with a quoted `filename` parameter when one is
|
|
150
|
+
* given.
|
|
151
|
+
*/
|
|
152
|
+
declare function createContentDispositionHeader(def: ContentDispositionDefinition): string;
|
|
153
|
+
/**
|
|
154
|
+
* Reads a header from any `HeadersInit` shape, without constructing a `Headers`.
|
|
155
|
+
*
|
|
156
|
+
* Header names are case-insensitive, so every shape is matched case-insensitively:
|
|
157
|
+
* a `Headers` instance is probed with both casings, and the array and object
|
|
158
|
+
* forms are scanned with lowercased comparison.
|
|
159
|
+
*
|
|
160
|
+
* @param headers - The headers to read, in any accepted form. `undefined` and
|
|
161
|
+
* `null` are allowed and yield `null`.
|
|
162
|
+
* @param name - The header to look for.
|
|
163
|
+
* @returns The value, or `null` when absent.
|
|
164
|
+
*/
|
|
165
|
+
declare function readHeader(headers: Optional<HeadersInit>, name: HeaderKey): Nullable<string>;
|
|
166
|
+
/**
|
|
167
|
+
* Installs the extended `Headers` behaviour declared above onto the global
|
|
168
|
+
* class. Call it once at startup, before any request is served.
|
|
169
|
+
*
|
|
170
|
+
* The patch is applied twice over, deliberately. The prototype methods are
|
|
171
|
+
* replaced so headers *the runtime* created — those on an incoming `Request`, or
|
|
172
|
+
* on a `Response` built elsewhere — gain the same behaviour. The global class is
|
|
173
|
+
* then also replaced with a subclass, so instances constructed after the patch
|
|
174
|
+
* carry the methods as own class members rather than only as prototype
|
|
175
|
+
* assignments.
|
|
176
|
+
*
|
|
177
|
+
* The subclass overrides `Symbol.hasInstance` to defer to the native class, so
|
|
178
|
+
* `instanceof Headers` stays true for objects the runtime created before or
|
|
179
|
+
* outside the patch. Without it, the swap would silently break every
|
|
180
|
+
* `instanceof` check against headers the framework did not construct.
|
|
181
|
+
*/
|
|
182
|
+
declare function patchGlobalHeaders(): void;
|
|
183
|
+
declare global {
|
|
184
|
+
/**
|
|
185
|
+
* The `Headers` surface after {@link patchGlobalHeaders} has run.
|
|
186
|
+
*
|
|
187
|
+
* The existing methods are re-declared to accept a {@link HeaderKey} and a
|
|
188
|
+
* {@link HeadersInitValue}; the rest are additions.
|
|
189
|
+
*/
|
|
190
|
+
interface Headers {
|
|
191
|
+
/** Adds a value without replacing existing ones. An array appends each item as its own header line. */
|
|
192
|
+
append(name: HeaderKey, value: MaybeArray<HeadersInitValue>): void;
|
|
193
|
+
/** Sets a header, replacing any existing value. Numbers and booleans are stringified. */
|
|
194
|
+
set(name: HeaderKey, value: HeadersInitValue): void;
|
|
195
|
+
/** Reads a header, falling back to the lowercased name. */
|
|
196
|
+
get(name: HeaderKey): Nullable<string>;
|
|
197
|
+
/** Reports whether a header is present, falling back to the lowercased name. */
|
|
198
|
+
has(name: HeaderKey): boolean;
|
|
199
|
+
/** Sets many headers at once. See {@link CustomHeadersInit}. */
|
|
200
|
+
setMany(init: CustomHeadersInit): void;
|
|
201
|
+
/** Sets `Cache-Control` from a {@link CacheControlDefinition}. */
|
|
202
|
+
setCacheControl(def: CacheControlDefinition): void;
|
|
203
|
+
/** Sets `Content-Disposition` from a {@link ContentDispositionDefinition}. */
|
|
204
|
+
setContentDisposition(def: ContentDispositionDefinition): void;
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
export { patchGlobalHeaders, createCacheControlHeader, createContentDispositionHeader, readHeader, HeaderKey, type ContentDispositionDefinition, type CacheControlDefinition, };
|
|
208
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/Headers/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Logic that runs around a route handler — before it, after it, or instead of
|
|
3
|
+
* it.
|
|
4
|
+
*
|
|
5
|
+
* A {@link Middleware} receives the {@link Context} and a `next` function. What
|
|
6
|
+
* runs before `await next()` happens on the way in; what runs after it happens
|
|
7
|
+
* on the way out, with the downstream result in hand. Returning early instead of
|
|
8
|
+
* calling `next()` short-circuits the chain, which is how authentication rejects
|
|
9
|
+
* a request without the route handler ever running.
|
|
10
|
+
*
|
|
11
|
+
* Constructing one registers it on the nearest {@link App}, which folds it into
|
|
12
|
+
* each targeted route's chain at compile time via {@link composeHandlerChain}.
|
|
13
|
+
* Targeting is by route id, but {@link Middleware.useOn} accepts routes and
|
|
14
|
+
* {@link Controller} instances directly and resolves the ids itself.
|
|
15
|
+
*
|
|
16
|
+
* ```ts
|
|
17
|
+
* import { Middleware } from "@ozanarslan/corpus";
|
|
18
|
+
*
|
|
19
|
+
* new Middleware({
|
|
20
|
+
* useOn: usersController,
|
|
21
|
+
* handler: async (c, next) => {
|
|
22
|
+
* const started = performance.now();
|
|
23
|
+
* const result = await next();
|
|
24
|
+
* c.res.headers.set("X-Response-Time", performance.now() - started);
|
|
25
|
+
* return result;
|
|
26
|
+
* },
|
|
27
|
+
* });
|
|
28
|
+
* ```
|
|
29
|
+
*
|
|
30
|
+
* @module Middleware
|
|
31
|
+
*/
|
|
32
|
+
import type { Context } from "../Context";
|
|
33
|
+
import type { Controller } from "../Controller";
|
|
34
|
+
import type { RouteBase } from "../RouteBase";
|
|
35
|
+
import type { MaybePromise, OrString } from "../utils/is";
|
|
36
|
+
/**
|
|
37
|
+
* A middleware's handler function. Like a {@link ContextHandler}, but with the
|
|
38
|
+
* rest of the chain passed in.
|
|
39
|
+
*
|
|
40
|
+
* What the return value means is resolved by {@link composeHandlerChain}: a
|
|
41
|
+
* returned value short-circuits the chain, `undefined` after calling `next()`
|
|
42
|
+
* passes the downstream result through, and `undefined` without calling `next()`
|
|
43
|
+
* lets the chain continue anyway.
|
|
44
|
+
*
|
|
45
|
+
* @param context - The {@link Context} for the request, shared with every other
|
|
46
|
+
* handler in the chain. Use {@link Context.data} to pass state downstream.
|
|
47
|
+
* @param next - Runs the rest of the chain and resolves to its result. Calling
|
|
48
|
+
* it more than once throws.
|
|
49
|
+
* @returns The response value, or `undefined` to defer to the chain.
|
|
50
|
+
* @typeParam R - The result type passed along the chain.
|
|
51
|
+
*/
|
|
52
|
+
type MiddlewareHandler<R = unknown> = (context: Context, next: () => MaybePromise<R>) => MaybePromise<R>;
|
|
53
|
+
/**
|
|
54
|
+
* What a middleware applies to.
|
|
55
|
+
*
|
|
56
|
+
* A {@link RouteBase} targets that route, a {@link Controller} targets every
|
|
57
|
+
* route registered through it, a string targets a route id directly, and an
|
|
58
|
+
* array combines any of these. The literal `"*"` targets every route on the app,
|
|
59
|
+
* including requests that match none — global middlewares also run ahead of
|
|
60
|
+
* {@link App.handleNotFound}.
|
|
61
|
+
*/
|
|
62
|
+
type MiddlewareUseOn = Array<RouteBase | Controller | string> | RouteBase | Controller | OrString<"*">;
|
|
63
|
+
/** Construction arguments for a {@link Middleware}. */
|
|
64
|
+
type MiddlewareDefinition = {
|
|
65
|
+
/** What the middleware applies to. Defaults to `"*"` — every route. */
|
|
66
|
+
useOn?: MiddlewareUseOn;
|
|
67
|
+
/** The {@link MiddlewareHandler} to run. */
|
|
68
|
+
handler: MiddlewareHandler;
|
|
69
|
+
};
|
|
70
|
+
/**
|
|
71
|
+
* A handler registered to run around some or all of an app's routes.
|
|
72
|
+
*
|
|
73
|
+
* Middlewares execute in the order {@link App.findMiddlewares} returns them:
|
|
74
|
+
* global ones first, then route-specific ones, then the route handler. Since the
|
|
75
|
+
* chain nests, a global middleware wraps everything after it — its post-`next()`
|
|
76
|
+
* code runs last.
|
|
77
|
+
*
|
|
78
|
+
* Targeting a route id that no route claims is not an error, but the middleware
|
|
79
|
+
* will never run; {@link App.warnUnmatchedMiddlewares} logs a warning at startup
|
|
80
|
+
* when that happens.
|
|
81
|
+
*/
|
|
82
|
+
declare class Middleware {
|
|
83
|
+
/**
|
|
84
|
+
* Creates a middleware for subclasses, which declare
|
|
85
|
+
* {@link Middleware.handler} and {@link Middleware.useOn} as class fields and
|
|
86
|
+
* call {@link Middleware.register} themselves.
|
|
87
|
+
*/
|
|
88
|
+
constructor();
|
|
89
|
+
/**
|
|
90
|
+
* Creates a middleware and registers it on the nearest {@link App}.
|
|
91
|
+
*
|
|
92
|
+
* @param definition - The {@link MiddlewareDefinition}: the handler, and
|
|
93
|
+
* optionally what it applies to.
|
|
94
|
+
*/
|
|
95
|
+
constructor(definition: MiddlewareDefinition);
|
|
96
|
+
/**
|
|
97
|
+
* Registers this middleware on the nearest {@link App} through
|
|
98
|
+
* {@link App.addMiddleware}. Called by the constructor.
|
|
99
|
+
*
|
|
100
|
+
* Registration order relative to routes does not matter — targets are resolved
|
|
101
|
+
* to ids here, and the app only matches them when it compiles routes.
|
|
102
|
+
*/
|
|
103
|
+
register(): void;
|
|
104
|
+
/**
|
|
105
|
+
* What this middleware applies to. Defaults to `"*"`, meaning every route on
|
|
106
|
+
* the app.
|
|
107
|
+
*/
|
|
108
|
+
useOn: MiddlewareUseOn;
|
|
109
|
+
/** The function that runs when a targeted route is hit. */
|
|
110
|
+
handler: MiddlewareHandler;
|
|
111
|
+
/**
|
|
112
|
+
* The route ids resolved from {@link Middleware.useOn}, which
|
|
113
|
+
* {@link App.addMiddleware} indexes the middleware under.
|
|
114
|
+
*
|
|
115
|
+
* Each target contributes its ids: a route its own, a {@link Controller} all
|
|
116
|
+
* of {@link Controller.routeIds}, and a string itself. Duplicates are
|
|
117
|
+
* collapsed, so a route listed both directly and through its controller is
|
|
118
|
+
* still wrapped once.
|
|
119
|
+
*
|
|
120
|
+
* @returns The ids, or `["*"]` for a global middleware.
|
|
121
|
+
*/
|
|
122
|
+
get routeIds(): Array<string>;
|
|
123
|
+
}
|
|
124
|
+
export { Middleware, type MiddlewareDefinition, type MiddlewareUseOn, type MiddlewareHandler };
|
|
125
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/Middleware/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AAEH,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACzC,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE/C,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AAE7C,OAAO,KAAK,EAAE,YAAY,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAEzD;;;;;;;;;;;;;;;GAeG;AACH,KAAK,iBAAiB,CAAC,CAAC,GAAG,OAAO,IAAI,CACrC,OAAO,EAAE,OAAO,EAChB,IAAI,EAAE,MAAM,YAAY,CAAC,CAAC,CAAC,KACvB,YAAY,CAAC,CAAC,CAAC,CAAC;AAErB;;;;;;;;GAQG;AACH,KAAK,eAAe,GACjB,KAAK,CAAC,SAAS,GAAG,UAAU,GAAG,MAAM,CAAC,GACtC,SAAS,GACT,UAAU,GACV,QAAQ,CAAC,GAAG,CAAC,CAAC;AAEjB,uDAAuD;AACvD,KAAK,oBAAoB,GAAG;IAC3B,uEAAuE;IACvE,KAAK,CAAC,EAAE,eAAe,CAAC;IACxB,4CAA4C;IAC5C,OAAO,EAAE,iBAAiB,CAAC;CAC3B,CAAC;AAEF;;;;;;;;;;;GAWG;AACH,cAAM,UAAU;IACf;;;;OAIG;;IAEH;;;;;OAKG;gBACS,UAAU,EAAE,oBAAoB;IAS5C;;;;;;OAMG;IACH,QAAQ,IAAI,IAAI;IAIhB;;;OAGG;IACH,KAAK,EAAE,eAAe,CAAO;IAE7B,2DAA2D;IAC3D,OAAO,EAAG,iBAAiB,CAAC;IAE5B;;;;;;;;;;OAUG;IACH,IAAI,QAAQ,IAAI,KAAK,CAAC,MAAM,CAAC,CAc5B;CACD;AAED,OAAO,EAAE,UAAU,EAAE,KAAK,oBAAoB,EAAE,KAAK,eAAe,EAAE,KAAK,iBAAiB,EAAE,CAAC"}
|