@supacloud/elysia 0.20.2 → 0.21.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,77 @@
1
+ import { type CompiledModule } from "../index";
2
+ export interface CatalogIdentity {
3
+ tenantId: string;
4
+ subject: string;
5
+ }
6
+ export interface CatalogItem {
7
+ id: string;
8
+ name: string;
9
+ }
10
+ export interface CatalogPorts {
11
+ /** Resolve credentials using a trusted verifier, never a tenant header alone. */
12
+ authenticate(request: Request): Promise<CatalogIdentity>;
13
+ /** The repository must apply this verified identity to its authorization. */
14
+ read(identity: CatalogIdentity, id: string): Promise<CatalogItem>;
15
+ }
16
+ /**
17
+ * A handwritten adapter fixture, not compiler output or a new module format.
18
+ * Real applications can supply the existing compiler's createCompiledModules().
19
+ */
20
+ export declare function createCatalogModule(ports: CatalogPorts): CompiledModule;
21
+ export declare function createCatalogApplication(ports: CatalogPorts): import("elysia/types").AddRoute<"", "local", {
22
+ decorator: {
23
+ clock: () => number;
24
+ };
25
+ store: {};
26
+ derive: {};
27
+ }, {
28
+ typebox: {};
29
+ error: [];
30
+ }, import("elysia").DefaultMetadata & {
31
+ schema: {};
32
+ schemas: {};
33
+ macro: {};
34
+ macroFn: {};
35
+ parser: {};
36
+ response: {};
37
+ }, {}, import("elysia").DefaultEphemeral, {
38
+ derive: {};
39
+ schema: {};
40
+ schemas: {};
41
+ response: {};
42
+ error: [];
43
+ }, "get", "/health", import("elysia/types").IntersectIfObjectSchema<import("elysia").UnwrapRoute<{}, {}, "/health">, import("elysia/types").MergeScopedSchemas<{}, {}, {}>>, {}, ({ clock }: {
44
+ body: unknown;
45
+ query: Record<string, string | undefined>;
46
+ params: {};
47
+ headers: Record<string, string | undefined>;
48
+ cookie: Record<string, import("elysia").Cookie<unknown>>;
49
+ server: import("elysia").Server | null;
50
+ redirect: import("elysia").redirect;
51
+ set: {
52
+ headers: import("elysia").HTTPHeaders;
53
+ status?: number | keyof import("elysia").StatusMap;
54
+ cookie?: Record<string, import("elysia").BaseCookie>;
55
+ redirect?: never;
56
+ };
57
+ status: <const Code extends number | keyof import("elysia").StatusMap, const T = import("elysia").StatusResponse<Code>>(code: Code, response?: T) => import("elysia").ElysiaStatus<Code, T, import("elysia").NumericStatus<Code>>;
58
+ problem: typeof import("elysia").problem;
59
+ defer: (fn: import("elysia/types").AfterResponseHandler<NoInfer<import("elysia/types").IntersectIfObjectSchema<import("elysia").UnwrapRoute<{}, {}, "/health">, import("elysia/types").MergeScopedSchemas<{}, {}, {}>>>, NoInfer<{
60
+ decorator: {
61
+ clock: () => number;
62
+ };
63
+ store: {};
64
+ derive: {};
65
+ } & {
66
+ derive: {};
67
+ }>>) => import("elysia/types").MaybePromise<void>;
68
+ readonly path: string;
69
+ route?: string | undefined;
70
+ rid?: string | undefined;
71
+ request: Request;
72
+ store: {};
73
+ clock: () => number;
74
+ }) => {
75
+ ok: boolean;
76
+ time: number;
77
+ }>;
@@ -1,13 +1,2 @@
1
- export interface ExecutionEvent {
2
- kind: "route" | "command" | "job";
3
- operation: string;
4
- stage: string;
5
- phase: "started" | "succeeded" | "failed";
6
- requestId?: string;
7
- durationMs?: number;
8
- }
9
- /** Metadata only: never receives request bodies, credentials, results or errors. */
10
- export type ExecutionObserver = (event: Readonly<ExecutionEvent>) => void | Promise<void>;
11
- export declare function observeExecution<T>(observer: ExecutionObserver | undefined, event: Pick<ExecutionEvent, "kind" | "operation" | "stage" | "requestId">, next: () => T | Promise<T>): Promise<T>;
12
- export declare function executionRequestId(context: unknown): string | undefined;
13
- export declare function executionTrace(context: unknown): Pick<ExecutionEvent, "requestId">;
1
+ export { executionRequestId, executionTrace, observeExecution, } from "@supacloud/app/execution";
2
+ export type { ExecutionEvent, ExecutionObserver } from "@supacloud/app/execution";
@@ -0,0 +1,39 @@
1
+ import type { AnyElysia, Elysia } from "elysia";
2
+ import { type ApplicationOptions, type CompiledModule } from "./index";
3
+ /**
4
+ * Experimental profile for evaluating SupaCloud application composition.
5
+ *
6
+ * This intentionally remains a thin profile over createApplication. It owns
7
+ * SupaCloud defaults without wrapping or reimplementing Elysia's API.
8
+ */
9
+ export interface SupaCloudFrameworkOptions<Http extends AnyElysia = Elysia, RequestContext = unknown> extends Omit<ApplicationOptions<Http, RequestContext>, "name" | "normalize" | "modules"> {
10
+ /** Application modules in compiler-emitted topological order. */
11
+ modules?: CompiledModule[];
12
+ /** Public application name used in diagnostics and Elysia plugin identity. */
13
+ name: string;
14
+ /**
15
+ * Reject extra properties rather than silently removing them.
16
+ */
17
+ normalize?: false;
18
+ }
19
+ export declare function createSupaCloudFramework<const Http extends AnyElysia = Elysia, RequestContext = unknown>(options: SupaCloudFrameworkOptions<Http, RequestContext>): Elysia<"", "local", {
20
+ decorator: {} & Http["~Singleton"]["decorator"];
21
+ store: ({} & Http["~Singleton"]["store"] extends infer T_1 ? { [K_1 in keyof T_1]: T_1[K_1]; } : never) extends infer T ? { [K in keyof T]: T[K]; } : never;
22
+ derive: {} & Http["~Singleton"]["derive"] & Http["~Ephemeral"]["derive"];
23
+ }, {
24
+ typebox: {} & Http["~Definitions"]["typebox"];
25
+ error: [...Http["~Definitions"]["error"], ...Http["~Ephemeral"]["error"]];
26
+ }, import("elysia").DefaultMetadata & {
27
+ schema: import("elysia/types").MergeSchema<import("elysia/types").MergeSchema<{} & Http["~Ephemeral"]["schema"], {}, "", false>, (import("elysia").DefaultMetadata & Http["~Metadata"])["schema"], "", false>;
28
+ schemas: (import("elysia").DefaultMetadata & Http["~Metadata"])["schemas"] & {} & Http["~Ephemeral"]["schemas"];
29
+ macro: (import("elysia").DefaultMetadata & Http["~Metadata"])["macro"];
30
+ macroFn: (import("elysia").DefaultMetadata & Http["~Metadata"])["macroFn"];
31
+ parser: (import("elysia").DefaultMetadata & Http["~Metadata"])["parser"];
32
+ response: import("elysia/types").UnionResponseStatus<(import("elysia").DefaultMetadata & Http["~Metadata"])["response"], import("elysia/types").UnionResponseStatus<{} & Http["~Ephemeral"]["response"], {}>>;
33
+ }, import("elysia/types").ResolveRouteErrors<{}, [...Http["~Definitions"]["error"], ...Http["~Ephemeral"]["error"]]> & Http["~Routes"], import("elysia").DefaultEphemeral, {
34
+ derive: {};
35
+ schema: {};
36
+ schemas: {};
37
+ response: {};
38
+ error: [];
39
+ }>;
package/dist/index.d.ts CHANGED
@@ -22,6 +22,8 @@ export type { ElysiaRouteContext, ElysiaRouteDefinition, ElysiaRouteHandler, Ely
22
22
  export { createPersistentCommandAdapter, type PersistentCommandHandler } from "./persistent-command";
23
23
  export { createDocumentationPlugin } from "./documentation";
24
24
  export type { ApplicationDocumentationOptions, DocumentationSource, GraphqlDocumentationOptions, OpenApiDocumentationOptions, } from "./documentation";
25
+ export { createSupaCloudFramework } from "./framework";
26
+ export type { SupaCloudFrameworkOptions } from "./framework";
25
27
  export interface CompiledRoute {
26
28
  parse?: "none";
27
29
  allowDeleteBody?: true;
package/dist/index.js CHANGED
@@ -662,39 +662,11 @@ function createPostgresHttpPolicyStores(database) {
662
662
  };
663
663
  }
664
664
  // src/execution.ts
665
- async function observeExecution(observer, event, next) {
666
- const emit = (phase, durationMs) => {
667
- if (!observer)
668
- return;
669
- try {
670
- Promise.resolve(observer(Object.freeze({
671
- ...event,
672
- phase,
673
- ...durationMs === undefined ? {} : { durationMs }
674
- }))).catch(() => {});
675
- } catch {}
676
- };
677
- const started = performance.now();
678
- emit("started");
679
- try {
680
- const result = await next();
681
- emit("succeeded", performance.now() - started);
682
- return result;
683
- } catch (error) {
684
- emit("failed", performance.now() - started);
685
- throw error;
686
- }
687
- }
688
- function executionRequestId(context) {
689
- if (!context || typeof context !== "object" || !("requestId" in context))
690
- return;
691
- const value = context.requestId;
692
- return typeof value === "string" && /^[A-Za-z0-9._:-]{1,256}$/.test(value) ? value : undefined;
693
- }
694
- function executionTrace(context) {
695
- const requestId = executionRequestId(context);
696
- return requestId === undefined ? {} : { requestId };
697
- }
665
+ import {
666
+ executionRequestId,
667
+ executionTrace,
668
+ observeExecution
669
+ } from "@supacloud/app/execution";
698
670
 
699
671
  // src/schema_contract.ts
700
672
  import {
@@ -1099,6 +1071,14 @@ function createPersistentCommandAdapter(command, options) {
1099
1071
  }
1100
1072
  };
1101
1073
  }
1074
+ // src/framework.ts
1075
+ function createSupaCloudFramework(options) {
1076
+ return createApplication({
1077
+ ...options,
1078
+ normalize: options.normalize ?? false,
1079
+ modules: options.modules ?? []
1080
+ });
1081
+ }
1102
1082
  // src/feature.ts
1103
1083
  function assertFeatureTransition(spec, state, event) {
1104
1084
  const transition = Object.hasOwn(spec.transitions, event) ? spec.transitions[event] : undefined;
@@ -2758,6 +2738,7 @@ export {
2758
2738
  createQueueWorkerTransport,
2759
2739
  createSchemaDecoder,
2760
2740
  createSupAuthRequestContext,
2741
+ createSupaCloudFramework,
2761
2742
  createSupaCloudRequestContext,
2762
2743
  createTestApp,
2763
2744
  createWorker,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@supacloud/elysia",
3
- "version": "0.20.2",
3
+ "version": "0.21.0",
4
4
  "description": "Elysia runtime adapter for SupaCloud compiled modules: application/request scopes, route registration and validation",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -28,7 +28,7 @@
28
28
  "clean": "rm -rf dist",
29
29
  "prepublishOnly": "bun run build",
30
30
  "test": "bun test",
31
- "test:conformance": "bun test src/conformance.test.ts",
31
+ "test:conformance": "bun test src/conformance.test.ts src/application-execution.test.ts ../app/src/execution.test.ts ../app/src/execution_bundle.test.ts",
32
32
  "test:runtime-safety": "SUPACLOUD_REQUIRE_RUNTIME_SAFETY=1 bun test src/runtime-safety.test.ts",
33
33
  "test:contract-upgrade": "bun test src/contract-upgrade.test.ts",
34
34
  "bench:http-policy": "bun bench/http-policy.ts",
@@ -49,25 +49,25 @@
49
49
  "directory": "packages/elysia"
50
50
  },
51
51
  "dependencies": {
52
- "@supacloud/app": "0.18.1",
53
- "@supacloud/contracts": "0.5.1",
52
+ "@supacloud/app": "0.19.0",
53
+ "@supacloud/contracts": "0.6.0",
54
54
  "exact-mirror": "1.2.6",
55
55
  "jose": "^6.2.11",
56
56
  "typebox": "1.3.34"
57
57
  },
58
58
  "overrides": {
59
- "@supacloud/delivery": "0.2.1",
60
- "@supacloud/contracts": "0.5.1",
61
- "@supacloud/commands": "0.7.1"
59
+ "@supacloud/delivery": "0.3.0",
60
+ "@supacloud/contracts": "0.6.0",
61
+ "@supacloud/commands": "0.8.0"
62
62
  },
63
63
  "peerDependencies": {
64
64
  "elysia": "2.0.0-beta.19"
65
65
  },
66
66
  "devDependencies": {
67
- "@supacloud/compiler": "0.27.4",
68
- "@supacloud/delivery": "0.2.1",
69
- "@supacloud/commands": "0.7.1",
70
- "@supacloud/db": "0.9.1",
67
+ "@supacloud/compiler": "0.28.0",
68
+ "@supacloud/delivery": "0.3.0",
69
+ "@supacloud/commands": "0.8.0",
70
+ "@supacloud/db": "0.10.0",
71
71
  "@types/bun": "^1.4.2",
72
72
  "elysia": "2.0.0-beta.19",
73
73
  "typescript": "^7.0.2"