@superbee/server 0.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.
@@ -0,0 +1,14 @@
1
+ /**
2
+ * `@superbee/server` — the wire-protocol v0 REFERENCE server
3
+ * (`docs/WIRE-PROTOCOL.md`): a Web-standard `fetch`-style router over the OKF
4
+ * engine, plus a thin `node:http` bootstrap. A pure consumer of
5
+ * `@superbee/core` — no parsing/link/OKF logic lives here (see `router.ts`
6
+ * module doc). Reference-not-production: no auth, loopback-only default bind.
7
+ *
8
+ * @packageDocumentation
9
+ */
10
+ export { createRouter, createRouterForBackend } from "./legacy-router.js";
11
+ export { WIRE_ENDPOINTS } from "./router.js";
12
+ export { RequestBodyTooLargeError, serve, requestFromIncomingMessage, writeResponseToServerResponse, } from "./serve.js";
13
+ export type { RequestAdapterOptions, ServeOptions, ServerHandle, } from "./serve.js";
14
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,EAAE,YAAY,EAAE,sBAAsB,EAAE,MAAM,oBAAoB,CAAC;AAC1E,OAAO,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAC7C,OAAO,EACL,wBAAwB,EACxB,KAAK,EACL,0BAA0B,EAC1B,6BAA6B,GAC9B,MAAM,YAAY,CAAC;AACpB,YAAY,EACV,qBAAqB,EACrB,YAAY,EACZ,YAAY,GACb,MAAM,YAAY,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,13 @@
1
+ /**
2
+ * `@superbee/server` — the wire-protocol v0 REFERENCE server
3
+ * (`docs/WIRE-PROTOCOL.md`): a Web-standard `fetch`-style router over the OKF
4
+ * engine, plus a thin `node:http` bootstrap. A pure consumer of
5
+ * `@superbee/core` — no parsing/link/OKF logic lives here (see `router.ts`
6
+ * module doc). Reference-not-production: no auth, loopback-only default bind.
7
+ *
8
+ * @packageDocumentation
9
+ */
10
+ export { createRouter, createRouterForBackend } from "./legacy-router.js";
11
+ export { WIRE_ENDPOINTS } from "./router.js";
12
+ export { RequestBodyTooLargeError, serve, requestFromIncomingMessage, writeResponseToServerResponse, } from "./serve.js";
13
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,OAAO,EAAE,YAAY,EAAE,sBAAsB,EAAE,MAAM,oBAAoB,CAAC;AAC1E,OAAO,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAC7C,OAAO,EACL,wBAAwB,EACxB,KAAK,EACL,0BAA0B,EAC1B,6BAA6B,GAC9B,MAAM,YAAY,CAAC"}
@@ -0,0 +1,7 @@
1
+ /** Node-specific compatibility adapter for the historical single-backend package root. */
2
+ import { type Bundle, type StorageBackend } from "@superbee/core";
3
+ /** Historical explicit-backend entry point retained at the Node package root. */
4
+ export declare function createRouterForBackend(backend: StorageBackend): (request: Request) => Promise<Response>;
5
+ /** Historical Bundle entry point retained at the Node package root, including `/bundles/default`. */
6
+ export declare function createRouter(bundle: Bundle): (request: Request) => Promise<Response>;
7
+ //# sourceMappingURL=legacy-router.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"legacy-router.d.ts","sourceRoot":"","sources":["../src/legacy-router.ts"],"names":[],"mappings":"AAAA,0FAA0F;AAE1F,OAAO,EAGL,KAAK,MAAM,EACX,KAAK,cAAc,EAEpB,MAAM,gBAAgB,CAAC;AAiDxB,iFAAiF;AACjF,wBAAgB,sBAAsB,CAAC,OAAO,EAAE,cAAc,GAAG,CAAC,OAAO,EAAE,OAAO,KAAK,OAAO,CAAC,QAAQ,CAAC,CAEvG;AAED,qGAAqG;AACrG,wBAAgB,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,CAAC,OAAO,EAAE,OAAO,KAAK,OAAO,CAAC,QAAQ,CAAC,CAEpF"}
@@ -0,0 +1,48 @@
1
+ /** Node-specific compatibility adapter for the historical single-backend package root. */
2
+ import { FilesystemBackend, MemoryBackend, } from "@superbee/core";
3
+ import { createRouter as createWorkerRouter, } from "./router.js";
4
+ const LEGACY_INTERNAL_BUNDLE_ID = "bnd_00000000000000000000000000000000";
5
+ function capabilitiesForBackend(backend) {
6
+ return (backend.capabilities?.() ?? {
7
+ enforced_cas: backend instanceof MemoryBackend,
8
+ blobs: true,
9
+ projections: true,
10
+ backlinks: false,
11
+ });
12
+ }
13
+ function legacyAttribution(request) {
14
+ const actor = request.headers.get("X-Actor")?.trim();
15
+ const agent = request.headers.get("X-Agent")?.trim();
16
+ return {
17
+ actor: actor || "unknown",
18
+ ...(agent ? { agent } : {}),
19
+ };
20
+ }
21
+ /**
22
+ * Map the old ignored bundle slot to one internal canonical id. This adapter is reachable only
23
+ * from the Node package root; `@superbee/server/router` never admits `default` or another alias.
24
+ */
25
+ function canonicalizeLegacyBundleRoute(request) {
26
+ const url = new URL(request.url);
27
+ const match = /^\/v0\/bundles\/([^/]+)\/(.*)$/.exec(url.pathname);
28
+ if (!match)
29
+ return request;
30
+ url.pathname = `/v0/bundles/${LEGACY_INTERNAL_BUNDLE_ID}/${match[2]}`;
31
+ return new Request(url, request);
32
+ }
33
+ function buildLegacyRouter(backend) {
34
+ const workerRouter = createWorkerRouter({
35
+ capabilities: capabilitiesForBackend(backend),
36
+ resolveContext: (request) => ({ backend, attribution: legacyAttribution(request) }),
37
+ });
38
+ return (request) => workerRouter(canonicalizeLegacyBundleRoute(request));
39
+ }
40
+ /** Historical explicit-backend entry point retained at the Node package root. */
41
+ export function createRouterForBackend(backend) {
42
+ return buildLegacyRouter(backend);
43
+ }
44
+ /** Historical Bundle entry point retained at the Node package root, including `/bundles/default`. */
45
+ export function createRouter(bundle) {
46
+ return buildLegacyRouter(bundle.backend ?? new FilesystemBackend(bundle.root));
47
+ }
48
+ //# sourceMappingURL=legacy-router.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"legacy-router.js","sourceRoot":"","sources":["../src/legacy-router.ts"],"names":[],"mappings":"AAAA,0FAA0F;AAE1F,OAAO,EACL,iBAAiB,EACjB,aAAa,GAId,MAAM,gBAAgB,CAAC;AAExB,OAAO,EACL,YAAY,IAAI,kBAAkB,GAEnC,MAAM,aAAa,CAAC;AAErB,MAAM,yBAAyB,GAAG,sCAAsC,CAAC;AAEzE,SAAS,sBAAsB,CAAC,OAAuB;IACrD,OAAO,CACL,OAAO,CAAC,YAAY,EAAE,EAAE,IAAI;QAC1B,YAAY,EAAE,OAAO,YAAY,aAAa;QAC9C,KAAK,EAAE,IAAI;QACX,WAAW,EAAE,IAAI;QACjB,SAAS,EAAE,KAAK;KACjB,CACF,CAAC;AACJ,CAAC;AAED,SAAS,iBAAiB,CAAC,OAAgB;IACzC,MAAM,KAAK,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,EAAE,IAAI,EAAE,CAAC;IACrD,MAAM,KAAK,GAAG,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,EAAE,IAAI,EAAE,CAAC;IACrD,OAAO;QACL,KAAK,EAAE,KAAK,IAAI,SAAS;QACzB,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KAC5B,CAAC;AACJ,CAAC;AAED;;;GAGG;AACH,SAAS,6BAA6B,CAAC,OAAgB;IACrD,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IACjC,MAAM,KAAK,GAAG,gCAAgC,CAAC,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;IAClE,IAAI,CAAC,KAAK;QAAE,OAAO,OAAO,CAAC;IAC3B,GAAG,CAAC,QAAQ,GAAG,eAAe,yBAAyB,IAAI,KAAK,CAAC,CAAC,CAAE,EAAE,CAAC;IACvE,OAAO,IAAI,OAAO,CAAC,GAAG,EAAE,OAAO,CAAC,CAAC;AACnC,CAAC;AAED,SAAS,iBAAiB,CAAC,OAAuB;IAChD,MAAM,YAAY,GAAG,kBAAkB,CAAC;QACtC,YAAY,EAAE,sBAAsB,CAAC,OAAO,CAAC;QAC7C,cAAc,EAAE,CAAC,OAAO,EAAE,EAAE,CAAC,CAAC,EAAE,OAAO,EAAE,WAAW,EAAE,iBAAiB,CAAC,OAAO,CAAC,EAAE,CAAC;KACpF,CAAC,CAAC;IACH,OAAO,CAAC,OAAO,EAAE,EAAE,CAAC,YAAY,CAAC,6BAA6B,CAAC,OAAO,CAAC,CAAC,CAAC;AAC3E,CAAC;AAED,iFAAiF;AACjF,MAAM,UAAU,sBAAsB,CAAC,OAAuB;IAC5D,OAAO,iBAAiB,CAAC,OAAO,CAAC,CAAC;AACpC,CAAC;AAED,qGAAqG;AACrG,MAAM,UAAU,YAAY,CAAC,MAAc;IACzC,OAAO,iBAAiB,CAAC,MAAM,CAAC,OAAO,IAAI,IAAI,iBAAiB,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC;AACjF,CAAC"}
@@ -0,0 +1,194 @@
1
+ /**
2
+ * Wire-protocol v0 fetch router — the wire-protocol v0 seam-over-HTTP contract
3
+ * (`docs/WIRE-PROTOCOL.md`) implemented as a plain
4
+ * `(req: Request) => Promise<Response>` function using Web-standard `Request`/
5
+ * `Response`, so the identical router can mount unchanged in another Fetch-compatible runtime.
6
+ *
7
+ * ONE-ENGINE RULE: this module contains NO parsing/link/OKF logic of its own.
8
+ * Doc WRITES route through the engine (`writeDocVersioned` from `@superbee/core`)
9
+ * so server-side OKF enforcement (non-empty `type`, id safety, reserved-file
10
+ * rejection) comes free — the engine keeps ALL semantics, the router only maps
11
+ * HTTP <-> the `StorageBackend` seam. Reads / list / versions / reserved-file
12
+ * access go through the bundle's `StorageBackend` DIRECTLY (protocol principle 2:
13
+ * "the seam is the schema" — every endpoint maps 1:1 to a seam method), not
14
+ * through the engine's `query`/`readDoc` wrappers.
15
+ *
16
+ * See `docs/WIRE-PROTOCOL.md` "Implemented by reference" section for the exact
17
+ * endpoint set and any recorded deviations from the draft.
18
+ */
19
+ import { type BlobKey, type ConceptId, type ReservedFilename, type StorageBackend, type StorageCapabilities } from "@superbee/core/storage";
20
+ /** Canonical remote bundle id: 16 random bytes rendered as lowercase hexadecimal. */
21
+ export type BundleId = `bnd_${string}`;
22
+ /** Access needed before a registered endpoint may dispatch. */
23
+ export type WireAccessClass = "public" | "read" | "write";
24
+ /**
25
+ * The complete public route/method registry for the reference router. Runtime dispatch consumes
26
+ * this table, and the repository contract test compares the same rows with WIRE-PROTOCOL.md, so a
27
+ * route cannot become reachable without entering the documented agreement surface.
28
+ */
29
+ export declare const WIRE_ENDPOINTS: readonly [{
30
+ readonly id: "capabilities";
31
+ readonly resource: "capabilities";
32
+ readonly method: "GET";
33
+ readonly path: "/v0/capabilities";
34
+ readonly accessClass: "public";
35
+ }, {
36
+ readonly id: "docs-list";
37
+ readonly resource: "docs";
38
+ readonly method: "GET";
39
+ readonly path: "/v0/bundles/{bundle}/docs";
40
+ readonly accessClass: "read";
41
+ }, {
42
+ readonly id: "docs-read-many";
43
+ readonly resource: "docs-read-many";
44
+ readonly method: "POST";
45
+ readonly path: "/v0/bundles/{bundle}/docs:read-many";
46
+ readonly accessClass: "read";
47
+ }, {
48
+ readonly id: "doc-read";
49
+ readonly resource: "doc";
50
+ readonly method: "GET";
51
+ readonly path: "/v0/bundles/{bundle}/docs/{id...}";
52
+ readonly accessClass: "read";
53
+ }, {
54
+ readonly id: "doc-write";
55
+ readonly resource: "doc";
56
+ readonly method: "PUT";
57
+ readonly path: "/v0/bundles/{bundle}/docs/{id...}";
58
+ readonly accessClass: "write";
59
+ }, {
60
+ readonly id: "doc-head";
61
+ readonly resource: "doc";
62
+ readonly method: "HEAD";
63
+ readonly path: "/v0/bundles/{bundle}/docs/{id...}";
64
+ readonly accessClass: "read";
65
+ }, {
66
+ readonly id: "doc-delete";
67
+ readonly resource: "doc";
68
+ readonly method: "DELETE";
69
+ readonly path: "/v0/bundles/{bundle}/docs/{id...}";
70
+ readonly accessClass: "write";
71
+ }, {
72
+ readonly id: "doc-versions";
73
+ readonly resource: "doc-versions";
74
+ readonly method: "GET";
75
+ readonly path: "/v0/bundles/{bundle}/docs/{id...}/versions";
76
+ readonly accessClass: "read";
77
+ }, {
78
+ readonly id: "reserved-read";
79
+ readonly resource: "reserved";
80
+ readonly method: "GET";
81
+ readonly path: "/v0/bundles/{bundle}/reserved/{name}";
82
+ readonly accessClass: "read";
83
+ }, {
84
+ readonly id: "reserved-write";
85
+ readonly resource: "reserved";
86
+ readonly method: "PUT";
87
+ readonly path: "/v0/bundles/{bundle}/reserved/{name}";
88
+ readonly accessClass: "write";
89
+ }, {
90
+ readonly id: "blobs-list";
91
+ readonly resource: "blobs";
92
+ readonly method: "GET";
93
+ readonly path: "/v0/bundles/{bundle}/blobs";
94
+ readonly accessClass: "read";
95
+ }, {
96
+ readonly id: "blob-read";
97
+ readonly resource: "blob";
98
+ readonly method: "GET";
99
+ readonly path: "/v0/bundles/{bundle}/blobs/{key...}";
100
+ readonly accessClass: "read";
101
+ }, {
102
+ readonly id: "blob-write";
103
+ readonly resource: "blob";
104
+ readonly method: "PUT";
105
+ readonly path: "/v0/bundles/{bundle}/blobs/{key...}";
106
+ readonly accessClass: "write";
107
+ }, {
108
+ readonly id: "blob-head";
109
+ readonly resource: "blob";
110
+ readonly method: "HEAD";
111
+ readonly path: "/v0/bundles/{bundle}/blobs/{key...}";
112
+ readonly accessClass: "read";
113
+ }, {
114
+ readonly id: "blob-delete";
115
+ readonly resource: "blob";
116
+ readonly method: "DELETE";
117
+ readonly path: "/v0/bundles/{bundle}/blobs/{key...}";
118
+ readonly accessClass: "write";
119
+ }];
120
+ export type WireEndpointId = (typeof WIRE_ENDPOINTS)[number]["id"];
121
+ export type ResolvedWireResource = {
122
+ kind: "capabilities";
123
+ } | {
124
+ kind: "docs";
125
+ } | {
126
+ kind: "docs-read-many";
127
+ } | {
128
+ kind: "doc";
129
+ id: ConceptId;
130
+ } | {
131
+ kind: "doc-versions";
132
+ id: ConceptId;
133
+ } | {
134
+ kind: "reserved";
135
+ dir: string;
136
+ name: ReservedFilename;
137
+ } | {
138
+ kind: "blobs";
139
+ } | {
140
+ kind: "blob";
141
+ key: BlobKey;
142
+ };
143
+ interface ResolvedWireRouteBase {
144
+ endpointId: WireEndpointId;
145
+ accessClass: WireAccessClass;
146
+ resource: ResolvedWireResource;
147
+ searchParams: URLSearchParams;
148
+ }
149
+ /** A deployment-scoped route never causes context or backend resolution. */
150
+ export interface ResolvedDeploymentWireRoute extends ResolvedWireRouteBase {
151
+ scope: "deployment";
152
+ endpointId: "capabilities";
153
+ accessClass: "public";
154
+ resource: {
155
+ kind: "capabilities";
156
+ };
157
+ }
158
+ /** A bundle-scoped route carries the one canonical bundle selection used by all later stages. */
159
+ export interface ResolvedBundleWireRoute extends ResolvedWireRouteBase {
160
+ scope: "bundle";
161
+ bundleId: BundleId;
162
+ accessClass: "read" | "write";
163
+ }
164
+ export type ResolvedWireRoute = ResolvedDeploymentWireRoute | ResolvedBundleWireRoute;
165
+ /** Attribution supplied by the trusted host after authentication, never by public request headers. */
166
+ export interface TrustedAttribution {
167
+ actor: string;
168
+ agent?: string;
169
+ }
170
+ /** The host's one-shot authorization result, including a backend already bound to `route.bundleId`. */
171
+ export interface TrustedRouterContext {
172
+ backend: StorageBackend;
173
+ attribution: TrustedAttribution;
174
+ }
175
+ export interface RouterOptions {
176
+ capabilities: StorageCapabilities;
177
+ resolveContext(request: Request, route: ResolvedBundleWireRoute): TrustedRouterContext | Response | Promise<TrustedRouterContext | Response>;
178
+ }
179
+ /** Typed resolution failure retained as a stable host-side rejection seam. */
180
+ export declare class WireRequestResolutionError extends Error {
181
+ readonly status: 400 | 404;
182
+ readonly code: "USAGE" | "NOT_FOUND";
183
+ constructor(status: 400 | 404, code: "USAGE" | "NOT_FOUND", message: string);
184
+ }
185
+ export declare function isCanonicalBundleId(value: string): value is BundleId;
186
+ /** Resolve route identity, canonical bundle selection, decoded resource, and access once. */
187
+ export declare function resolveWireRequest(request: Request): ResolvedWireRoute;
188
+ /**
189
+ * Build the fetch-style router for Worker runtimes. Bundle routes resolve context exactly once
190
+ * after canonical route resolution; deployment capabilities bypass context and storage entirely.
191
+ */
192
+ export declare function createRouter(options: RouterOptions): (req: Request) => Promise<Response>;
193
+ export {};
194
+ //# sourceMappingURL=router.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"router.d.ts","sourceRoot":"","sources":["../src/router.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAEH,OAAO,EASL,KAAK,OAAO,EACZ,KAAK,SAAS,EAGd,KAAK,gBAAgB,EACrB,KAAK,cAAc,EACnB,KAAK,mBAAmB,EAGzB,MAAM,wBAAwB,CAAC;AAsIhC,qFAAqF;AACrF,MAAM,MAAM,QAAQ,GAAG,OAAO,MAAM,EAAE,CAAC;AAEvC,+DAA+D;AAC/D,MAAM,MAAM,eAAe,GAAG,QAAQ,GAAG,MAAM,GAAG,OAAO,CAAC;AAE1D;;;;GAIG;AACH,eAAO,MAAM,cAAc;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;EA0GjB,CAAC;AAGX,MAAM,MAAM,cAAc,GAAG,CAAC,OAAO,cAAc,CAAC,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,CAAC;AAKnE,MAAM,MAAM,oBAAoB,GAC5B;IAAE,IAAI,EAAE,cAAc,CAAA;CAAE,GACxB;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAChB;IAAE,IAAI,EAAE,gBAAgB,CAAA;CAAE,GAC1B;IAAE,IAAI,EAAE,KAAK,CAAC;IAAC,EAAE,EAAE,SAAS,CAAA;CAAE,GAC9B;IAAE,IAAI,EAAE,cAAc,CAAC;IAAC,EAAE,EAAE,SAAS,CAAA;CAAE,GACvC;IAAE,IAAI,EAAE,UAAU,CAAC;IAAC,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,gBAAgB,CAAA;CAAE,GACzD;IAAE,IAAI,EAAE,OAAO,CAAA;CAAE,GACjB;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,GAAG,EAAE,OAAO,CAAA;CAAE,CAAC;AAEnC,UAAU,qBAAqB;IAC7B,UAAU,EAAE,cAAc,CAAC;IAC3B,WAAW,EAAE,eAAe,CAAC;IAC7B,QAAQ,EAAE,oBAAoB,CAAC;IAC/B,YAAY,EAAE,eAAe,CAAC;CAC/B;AAED,4EAA4E;AAC5E,MAAM,WAAW,2BAA4B,SAAQ,qBAAqB;IACxE,KAAK,EAAE,YAAY,CAAC;IACpB,UAAU,EAAE,cAAc,CAAC;IAC3B,WAAW,EAAE,QAAQ,CAAC;IACtB,QAAQ,EAAE;QAAE,IAAI,EAAE,cAAc,CAAA;KAAE,CAAC;CACpC;AAED,iGAAiG;AACjG,MAAM,WAAW,uBAAwB,SAAQ,qBAAqB;IACpE,KAAK,EAAE,QAAQ,CAAC;IAChB,QAAQ,EAAE,QAAQ,CAAC;IACnB,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC;CAC/B;AAED,MAAM,MAAM,iBAAiB,GAAG,2BAA2B,GAAG,uBAAuB,CAAC;AAEtF,sGAAsG;AACtG,MAAM,WAAW,kBAAkB;IACjC,KAAK,EAAE,MAAM,CAAC;IACd,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,uGAAuG;AACvG,MAAM,WAAW,oBAAoB;IACnC,OAAO,EAAE,cAAc,CAAC;IACxB,WAAW,EAAE,kBAAkB,CAAC;CACjC;AAED,MAAM,WAAW,aAAa;IAC5B,YAAY,EAAE,mBAAmB,CAAC;IAClC,cAAc,CACZ,OAAO,EAAE,OAAO,EAChB,KAAK,EAAE,uBAAuB,GAC7B,oBAAoB,GAAG,QAAQ,GAAG,OAAO,CAAC,oBAAoB,GAAG,QAAQ,CAAC,CAAC;CAC/E;AAED,8EAA8E;AAC9E,qBAAa,0BAA2B,SAAQ,KAAK;IACnD,QAAQ,CAAC,MAAM,EAAE,GAAG,GAAG,GAAG,CAAC;IAC3B,QAAQ,CAAC,IAAI,EAAE,OAAO,GAAG,WAAW,CAAC;gBAEzB,MAAM,EAAE,GAAG,GAAG,GAAG,EAAE,IAAI,EAAE,OAAO,GAAG,WAAW,EAAE,OAAO,EAAE,MAAM;CAM5E;AAID,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,MAAM,GAAG,KAAK,IAAI,QAAQ,CAEpE;AA8ID,6FAA6F;AAC7F,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,OAAO,GAAG,iBAAiB,CAUtE;AA8ED;;;GAGG;AACH,wBAAgB,YAAY,CAAC,OAAO,EAAE,aAAa,GAAG,CAAC,GAAG,EAAE,OAAO,KAAK,OAAO,CAAC,QAAQ,CAAC,CAExF"}