@lunora/codegen 1.0.0-alpha.42 → 1.0.0-alpha.44
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/dist/index.d.mts +155 -11
- package/dist/index.d.ts +155 -11
- package/dist/index.mjs +19 -18
- package/dist/packem_shared/AGENTS_FILENAME-BksnAJgx.mjs +116 -0
- package/dist/packem_shared/{FLAGS_FILENAME-fEZtzWXi.mjs → FLAGS_FILENAME-Dg4mKUuz.mjs} +1 -1
- package/dist/packem_shared/GENERATED_HEADER-7W9f2IG3.mjs +4 -0
- package/dist/packem_shared/{OPENRPC_VERSION-CzhfvCIQ.mjs → OPENRPC_VERSION-Cyttekkt.mjs} +1 -1
- package/dist/packem_shared/{SCHEMA_SNAPSHOT_FILENAME-Cl1EBMdR.mjs → SCHEMA_SNAPSHOT_FILENAME-CMjGZSa1.mjs} +80 -21
- package/dist/packem_shared/{buildOpenApiDocument-bg-NnLka.mjs → buildOpenApiDocument-saZ_-kl4.mjs} +1 -1
- package/dist/packem_shared/{discoverAuthApiCalls-WMx8L2FG.mjs → discoverAuthApiCalls-Dx3K42rk.mjs} +1 -1
- package/dist/packem_shared/{discoverCrons-D-jrpm97.mjs → discoverCrons-_aosTRLr.mjs} +36 -21
- package/dist/packem_shared/{discoverFunctions-CZ91aenA.mjs → discoverFunctions-BJ-qR7Rg.mjs} +1 -1
- package/dist/packem_shared/{discoverHttpRoutes-DNZLDCmm.mjs → discoverHttpRoutes-daCzuTe8.mjs} +9 -1
- package/dist/packem_shared/{discoverInserts-DFRJhmCv.mjs → discoverInserts-DI4q5NxE.mjs} +1 -1
- package/dist/packem_shared/{discoverMaskProcedures-B5iFnZ-X.mjs → discoverMaskProcedures-BcTOEKNU.mjs} +1 -1
- package/dist/packem_shared/{discoverMigrations-CdKtMlBc.mjs → discoverMigrations-VNUFvCwr.mjs} +1 -1
- package/dist/packem_shared/{discoverNondeterministicCalls-C_PrQPkA.mjs → discoverNondeterministicCalls-S0N2xLCq.mjs} +1 -1
- package/dist/packem_shared/{discoverQueries-B8W9UPrt.mjs → discoverQueries-CJnnnLpd.mjs} +1 -1
- package/dist/packem_shared/{discoverR2sqlCalls-Bm7Rfnf4.mjs → discoverR2sqlCalls-pnpicWfz.mjs} +1 -1
- package/dist/packem_shared/{discoverRlsMetadata-B4GL4ZKm.mjs → discoverRlsMetadata-DppniPUH.mjs} +1 -1
- package/dist/packem_shared/{discoverStorageRulesMetadata-nosjYcvN.mjs → discoverStorageRulesMetadata-CnHl2rXD.mjs} +1 -1
- package/dist/packem_shared/{emit-31Yg1Ee5.mjs → emit-C_29WVlW.mjs} +328 -31
- package/dist/packem_shared/{emitApp-DCP7Pr6M.mjs → emitApp-C9oljiZd.mjs} +25 -2
- package/package.json +9 -8
- package/dist/packem_shared/GENERATED_HEADER-D6RK1WF1.mjs +0 -3
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { agentComponent } from '@lunora/agent/component';
|
|
1
2
|
import { LunoraError } from '@lunora/errors';
|
|
2
3
|
import { s as sanitizeNamespace } from './paths-BRd6JHuF.mjs';
|
|
3
4
|
|
|
@@ -696,19 +697,19 @@ ${members}
|
|
|
696
697
|
};
|
|
697
698
|
return [...namespaces.entries()].toSorted(([a], [b]) => a.localeCompare(b)).map((entry) => renderNamespace(entry)).join("\n");
|
|
698
699
|
};
|
|
699
|
-
const
|
|
700
|
-
if (workflows.length === 0) {
|
|
700
|
+
const renderSchedulerReferences = (workflows, agents) => {
|
|
701
|
+
if (workflows.length === 0 && agents.length === 0) {
|
|
701
702
|
return { block: "", importLine: "" };
|
|
702
703
|
}
|
|
703
|
-
const
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
).join("\n");
|
|
708
|
-
const block = `
|
|
704
|
+
const importLines = [];
|
|
705
|
+
let block = "";
|
|
706
|
+
if (workflows.length > 0) {
|
|
707
|
+
block += `
|
|
709
708
|
/** Params type carried by a \`defineWorkflow\` definition (its phantom \`__params\`). */
|
|
710
709
|
type WorkflowParamsOf<Definition> = Definition extends { __params?: infer Params } ? (unknown extends Params ? Record<string, unknown> : Params) : Record<string, unknown>;
|
|
711
|
-
|
|
710
|
+
`;
|
|
711
|
+
}
|
|
712
|
+
block += `
|
|
712
713
|
/** A typed reference to a durable workflow, addressable for \`cronJobs()\` targets. Mirrors \`@lunora/scheduler\`'s \`WorkflowReference\` structurally. */
|
|
713
714
|
export interface WorkflowReference<Params = Record<string, unknown>> {
|
|
714
715
|
readonly isLunoraWorkflow: true;
|
|
@@ -716,7 +717,14 @@ export interface WorkflowReference<Params = Record<string, unknown>> {
|
|
|
716
717
|
readonly binding: string;
|
|
717
718
|
readonly name: string;
|
|
718
719
|
}
|
|
719
|
-
|
|
720
|
+
`;
|
|
721
|
+
if (workflows.length > 0) {
|
|
722
|
+
const sorted = [...workflows].toSorted((a, b) => a.exportName.localeCompare(b.exportName));
|
|
723
|
+
const refMembers = sorted.map((workflow) => ` ${workflow.exportName}: WorkflowReference<WorkflowParamsOf<typeof lunoraWorkflowDefinitions.${workflow.exportName}>>;`).join("\n");
|
|
724
|
+
const objectMembers = sorted.map(
|
|
725
|
+
(workflow) => ` ${workflow.exportName}: { isLunoraWorkflow: true, binding: ${JSON.stringify(workflow.bindingName)}, name: ${JSON.stringify(workflow.exportName)} },`
|
|
726
|
+
).join("\n");
|
|
727
|
+
block += `
|
|
720
728
|
/** This project's durable workflows, addressable as typed references (e.g. \`crons.daily("digest", …, workflows.digestPipeline, params)\`). */
|
|
721
729
|
export interface WorkflowsRef {
|
|
722
730
|
${refMembers}
|
|
@@ -726,17 +734,189 @@ export const workflows: WorkflowsRef = {
|
|
|
726
734
|
${objectMembers}
|
|
727
735
|
};
|
|
728
736
|
`;
|
|
729
|
-
|
|
730
|
-
`
|
|
737
|
+
importLines.push(`import type * as lunoraWorkflowDefinitions from "../workflows.js";
|
|
738
|
+
`);
|
|
739
|
+
}
|
|
740
|
+
if (agents.length > 0) {
|
|
741
|
+
const sorted = [...agents].toSorted((a, b) => a.exportName.localeCompare(b.exportName));
|
|
742
|
+
const refMembers = sorted.map((agent) => ` ${agent.exportName}: WorkflowReference<AgentRunInput>;`).join("\n");
|
|
743
|
+
const objectMembers = sorted.map(
|
|
744
|
+
(agent) => ` ${agent.exportName}: { isLunoraWorkflow: true, binding: ${JSON.stringify(agent.bindingName)}, name: ${JSON.stringify(agent.name)} },`
|
|
745
|
+
).join("\n");
|
|
746
|
+
block += `
|
|
747
|
+
/** This project's durable agents, addressable as typed references for \`cronJobs()\` — each fire starts a fresh agent run (e.g. \`crons.daily("sweep", …, agents.support, { input, threadKey })\`). */
|
|
748
|
+
export interface AgentsRef {
|
|
749
|
+
${refMembers}
|
|
750
|
+
}
|
|
751
|
+
|
|
752
|
+
export const agents: AgentsRef = {
|
|
753
|
+
${objectMembers}
|
|
754
|
+
};
|
|
755
|
+
`;
|
|
756
|
+
importLines.push(`import type { AgentRunInput } from "@lunora/agent";
|
|
757
|
+
`);
|
|
758
|
+
}
|
|
759
|
+
return { block, importLine: importLines.join("") };
|
|
760
|
+
};
|
|
761
|
+
const agentRuntimeFunctionNames = () => Object.keys(agentComponent().functions).toSorted((a, b) => a.localeCompare(b));
|
|
762
|
+
const takenAgentFunctionNames = (functions) => new Set(functions.filter((definition) => sanitizeNamespace(definition.filePath) === "agents").map((definition) => definition.exportName));
|
|
763
|
+
const renderAgentFunctionRegistry = (agents, functions) => {
|
|
764
|
+
const empty = { importLine: "", lines: "", prelude: "" };
|
|
765
|
+
if (agents.length === 0) {
|
|
766
|
+
return empty;
|
|
767
|
+
}
|
|
768
|
+
const taken = takenAgentFunctionNames(functions);
|
|
769
|
+
const names = agentRuntimeFunctionNames().filter((name) => !taken.has(name));
|
|
770
|
+
if (names.length === 0) {
|
|
771
|
+
return empty;
|
|
772
|
+
}
|
|
773
|
+
return {
|
|
774
|
+
importLine: 'import { agentComponent } from "@lunora/agent/component";\n',
|
|
775
|
+
lines: names.map((name) => ` "agents:${name}": lunoraAgentRuntimeFunctions.${name} as unknown as RegisteredLunoraFunction,`).join("\n"),
|
|
776
|
+
prelude: "\n/**\n * The `@lunora/agent` runtime component — auto-registered because `lunora/agents.ts`\n * declares agents. The durable loop dispatches the internal mutations; clients\n * subscribe to the public queries (`agents:agentMessages` is the live thread view).\n */\nconst lunoraAgentRuntimeFunctions = agentComponent().functions;\n"
|
|
777
|
+
};
|
|
778
|
+
};
|
|
779
|
+
const renderSandboxFunctionRegistry = (usesSandbox, functions) => {
|
|
780
|
+
if (!usesSandbox) {
|
|
781
|
+
return { importLine: "", lines: "", prelude: "" };
|
|
782
|
+
}
|
|
783
|
+
const collision = functions.find((definition) => sanitizeNamespace(definition.filePath) === "sandbox" && definition.exportName === "invoke");
|
|
784
|
+
if (collision) {
|
|
785
|
+
throw new LunoraError(
|
|
786
|
+
"INTERNAL",
|
|
787
|
+
`@lunora/codegen: "sandbox:invoke" is reserved for the batteries-included sandbox tool dispatcher (browserTool/containerTool) — rename the "invoke" export in ${collision.filePath}`
|
|
788
|
+
);
|
|
789
|
+
}
|
|
790
|
+
return {
|
|
791
|
+
importLine: 'import { sandboxComponent } from "@lunora/agent/component";\n',
|
|
792
|
+
lines: ' "sandbox:invoke": lunoraSandbox.invoke as unknown as RegisteredLunoraFunction,',
|
|
793
|
+
prelude: "\n/**\n * The `@lunora/agent` sandbox dispatcher — auto-registered because `lunora/`\n * imports a sandbox tool (`browserTool`/`containerTool`). The batteries-included\n * tools dispatch to this internal action, which runs on an action ctx carrying\n * `ctx.browser` + `ctx.containers` (the durable tool step itself has neither).\n */\nconst lunoraSandbox = sandboxComponent();\n"
|
|
794
|
+
};
|
|
731
795
|
};
|
|
732
|
-
const
|
|
796
|
+
const syntheticAgentApiFunctions = (agents, functions) => {
|
|
797
|
+
if (agents.length === 0) {
|
|
798
|
+
return [];
|
|
799
|
+
}
|
|
800
|
+
const taken = takenAgentFunctionNames(functions);
|
|
801
|
+
const definitions = [
|
|
802
|
+
{
|
|
803
|
+
args: { key: { kind: "string" }, limit: { inner: { kind: "number" }, kind: "optional" } },
|
|
804
|
+
exportName: "agentMessages",
|
|
805
|
+
filePath: "agents",
|
|
806
|
+
kind: "query",
|
|
807
|
+
returnType: "Record<string, unknown>[]"
|
|
808
|
+
},
|
|
809
|
+
{
|
|
810
|
+
args: {
|
|
811
|
+
decision: {
|
|
812
|
+
kind: "union",
|
|
813
|
+
members: [
|
|
814
|
+
{ kind: "literal", literalValue: '"approve"' },
|
|
815
|
+
{ kind: "literal", literalValue: '"reject"' }
|
|
816
|
+
]
|
|
817
|
+
},
|
|
818
|
+
instanceId: { kind: "string" },
|
|
819
|
+
note: { inner: { kind: "string" }, kind: "optional" },
|
|
820
|
+
threadKey: { kind: "string" },
|
|
821
|
+
toolCallId: { kind: "string" }
|
|
822
|
+
},
|
|
823
|
+
exportName: "agentResolveApproval",
|
|
824
|
+
filePath: "agents",
|
|
825
|
+
kind: "mutation",
|
|
826
|
+
returnType: "{ resolved: boolean }"
|
|
827
|
+
},
|
|
828
|
+
{
|
|
829
|
+
args: {
|
|
830
|
+
agent: { kind: "string" },
|
|
831
|
+
input: { kind: "string" },
|
|
832
|
+
threadKey: { kind: "string" },
|
|
833
|
+
title: { inner: { kind: "string" }, kind: "optional" }
|
|
834
|
+
},
|
|
835
|
+
exportName: "agentRun",
|
|
836
|
+
filePath: "agents",
|
|
837
|
+
kind: "mutation",
|
|
838
|
+
returnType: "{ id: string; threadKey: string }"
|
|
839
|
+
},
|
|
840
|
+
{
|
|
841
|
+
args: { key: { kind: "string" } },
|
|
842
|
+
exportName: "agentState",
|
|
843
|
+
filePath: "agents",
|
|
844
|
+
kind: "query",
|
|
845
|
+
returnType: "Record<string, unknown> | undefined"
|
|
846
|
+
},
|
|
847
|
+
{
|
|
848
|
+
args: { key: { kind: "string" } },
|
|
849
|
+
exportName: "agentThread",
|
|
850
|
+
filePath: "agents",
|
|
851
|
+
kind: "query",
|
|
852
|
+
returnType: "Record<string, unknown> | undefined"
|
|
853
|
+
}
|
|
854
|
+
];
|
|
855
|
+
for (const agent of agents) {
|
|
856
|
+
if (agent.voice) {
|
|
857
|
+
definitions.push({
|
|
858
|
+
args: { threadKey: { kind: "string" } },
|
|
859
|
+
exportName: `${agent.exportName}Voice`,
|
|
860
|
+
filePath: "agents",
|
|
861
|
+
kind: "stream",
|
|
862
|
+
returnType: "Record<string, unknown>"
|
|
863
|
+
});
|
|
864
|
+
}
|
|
865
|
+
}
|
|
866
|
+
return definitions.filter((definition) => !taken.has(definition.exportName));
|
|
867
|
+
};
|
|
868
|
+
const renderHttpStreamsRef = (httpRoutes) => {
|
|
869
|
+
const streams = httpRoutes.filter((route) => route.stream);
|
|
870
|
+
if (streams.length === 0) {
|
|
871
|
+
return { block: "", body: "" };
|
|
872
|
+
}
|
|
873
|
+
const namespaces = /* @__PURE__ */ new Map();
|
|
874
|
+
for (const route of streams) {
|
|
875
|
+
const list = namespaces.get(route.filePath) ?? [];
|
|
876
|
+
list.push(route);
|
|
877
|
+
namespaces.set(route.filePath, list);
|
|
878
|
+
}
|
|
879
|
+
const sortedNamespaces = [...namespaces.entries()].toSorted(([a], [b]) => a.localeCompare(b));
|
|
880
|
+
const typeBody = sortedNamespaces.map(([file, list]) => {
|
|
881
|
+
const members = list.map((route) => {
|
|
882
|
+
const chunkType = relocateGeneratedImports(route.chunkType ?? "unknown");
|
|
883
|
+
return ` ${renderPropertyKey(route.exportName)}: HttpStreamRef<${chunkType}, ${renderArgsType(route.searchParams)}, ${renderArgsType(route.params)}>;`;
|
|
884
|
+
}).join("\n");
|
|
885
|
+
return ` ${renderPropertyKey(sanitizeNamespace(file))}: {
|
|
886
|
+
${members}
|
|
887
|
+
};`;
|
|
888
|
+
}).join("\n");
|
|
889
|
+
const valueBody = sortedNamespaces.map(([file, list]) => {
|
|
890
|
+
const members = list.map(
|
|
891
|
+
(route) => ` ${renderPropertyKey(route.exportName)}: { method: ${JSON.stringify(route.method)}, path: ${JSON.stringify(route.path)} },`
|
|
892
|
+
).join("\n");
|
|
893
|
+
return ` ${renderPropertyKey(sanitizeNamespace(file))}: {
|
|
894
|
+
${members}
|
|
895
|
+
},`;
|
|
896
|
+
}).join("\n");
|
|
897
|
+
const block = `
|
|
898
|
+
/** This project's HTTP-SSE stream routes (\`httpRoute.<verb>(path).stream()\`), addressable as typed references for \`client.httpStream\` / \`useHttpStream\`. */
|
|
899
|
+
export interface HttpStreamsRef {
|
|
900
|
+
${typeBody}
|
|
901
|
+
}
|
|
902
|
+
|
|
903
|
+
export const httpStreams: HttpStreamsRef = {
|
|
904
|
+
${valueBody}
|
|
905
|
+
};
|
|
906
|
+
`;
|
|
907
|
+
return { block, body: typeBody };
|
|
908
|
+
};
|
|
909
|
+
const emitApi = (options) => {
|
|
910
|
+
const { agents = [], functions, httpRoutes = [], useUmbrella = false, workflows = [] } = options;
|
|
733
911
|
const base = baseSpecifiers(useUmbrella);
|
|
734
|
-
const publicFunctions = functions.filter((definition) => definition.visibility !== "internal");
|
|
912
|
+
const publicFunctions = [...functions.filter((definition) => definition.visibility !== "internal"), ...syntheticAgentApiFunctions(agents, functions)];
|
|
735
913
|
const internalFunctions = functions.filter((definition) => definition.visibility === "internal");
|
|
736
914
|
const publicBody = renderApiBody(publicFunctions);
|
|
737
915
|
const internalBody = renderApiBody(internalFunctions);
|
|
916
|
+
const httpStreamsRef = renderHttpStreamsRef(httpRoutes);
|
|
738
917
|
const combinedBody = `${publicBody}
|
|
739
|
-
${internalBody}
|
|
918
|
+
${internalBody}
|
|
919
|
+
${httpStreamsRef.body}`;
|
|
740
920
|
const dataModelImports = referencedDataModelImports(combinedBody);
|
|
741
921
|
const dataModelImportLine = dataModelImports.length > 0 ? `
|
|
742
922
|
import type { ${dataModelImports.join(", ")} } from "./dataModel.js";
|
|
@@ -747,10 +927,11 @@ ${publicBody}
|
|
|
747
927
|
const internalBlock = internalBody ? `
|
|
748
928
|
${internalBody}
|
|
749
929
|
` : "";
|
|
750
|
-
const
|
|
930
|
+
const schedulerReferences = renderSchedulerReferences(workflows, agents);
|
|
931
|
+
const clientImports = httpStreamsRef.block === "" ? "FunctionReference" : "FunctionReference, HttpStreamRef";
|
|
751
932
|
return `${GENERATED_HEADER}import { anyApi } from "${base.serverTypes}";
|
|
752
|
-
import type {
|
|
753
|
-
${
|
|
933
|
+
import type { ${clientImports} } from "${base.client}";
|
|
934
|
+
${schedulerReferences.importLine}${dataModelImportLine}
|
|
754
935
|
export interface ApiTypes {${apiBlock}}
|
|
755
936
|
|
|
756
937
|
export const api = anyApi as unknown as ApiTypes;
|
|
@@ -759,7 +940,7 @@ export const api = anyApi as unknown as ApiTypes;
|
|
|
759
940
|
export interface InternalApiTypes {${internalBlock}}
|
|
760
941
|
|
|
761
942
|
export const internal = anyApi as unknown as InternalApiTypes;
|
|
762
|
-
${
|
|
943
|
+
${schedulerReferences.block}${httpStreamsRef.block}`;
|
|
763
944
|
};
|
|
764
945
|
const emitSeed = (enabled) => {
|
|
765
946
|
if (!enabled) {
|
|
@@ -928,6 +1109,7 @@ const buildStorageBucketNames = (schema, ruleBuckets = []) => {
|
|
|
928
1109
|
return ["default", ...[...named].toSorted((a, b) => a.localeCompare(b))];
|
|
929
1110
|
};
|
|
930
1111
|
const emitServer = ({
|
|
1112
|
+
agents = [],
|
|
931
1113
|
containers = [],
|
|
932
1114
|
env,
|
|
933
1115
|
hasAccessFacade = false,
|
|
@@ -986,6 +1168,11 @@ const emitServer = ({
|
|
|
986
1168
|
assertIdentifier(queue.bindingName, `queue binding "${queue.bindingName}"`);
|
|
987
1169
|
return ` /** Queue producer binding for the \`${queue.exportName}\` queue. */
|
|
988
1170
|
readonly ${queue.bindingName}?: unknown;`;
|
|
1171
|
+
}),
|
|
1172
|
+
...agents.map((agent) => {
|
|
1173
|
+
assertIdentifier(agent.bindingName, `agent binding "${agent.bindingName}"`);
|
|
1174
|
+
return ` /** Workflow binding for the \`${agent.exportName}\` agent. */
|
|
1175
|
+
readonly ${agent.bindingName}?: unknown;`;
|
|
989
1176
|
})
|
|
990
1177
|
].join("\n");
|
|
991
1178
|
const envBlock = `
|
|
@@ -1056,6 +1243,20 @@ ${queues.map((queue) => ` readonly ${queue.exportName}: QueueProducer<QueueBo
|
|
|
1056
1243
|
}` : "";
|
|
1057
1244
|
const queuesContextField = hasQueues ? `
|
|
1058
1245
|
readonly queues: LunoraQueues;` : "";
|
|
1246
|
+
const hasAgents = agents.length > 0;
|
|
1247
|
+
const agentsTypeImport = hasAgents ? `import type { AgentHandle } from "@lunora/agent";
|
|
1248
|
+
` : "";
|
|
1249
|
+
const agentsTypeBlock = hasAgents ? `
|
|
1250
|
+
|
|
1251
|
+
/** This project's declared agents, addressable from \`ctx.agents\` by their \`lunora/agents.ts\` export name. */
|
|
1252
|
+
export interface LunoraAgents {
|
|
1253
|
+
${agents.map((agent) => {
|
|
1254
|
+
assertIdentifier(agent.exportName, `agent export "${agent.exportName}"`);
|
|
1255
|
+
return ` readonly ${agent.exportName}: AgentHandle;`;
|
|
1256
|
+
}).join("\n")}
|
|
1257
|
+
}` : "";
|
|
1258
|
+
const agentsContextField = hasAgents ? `
|
|
1259
|
+
readonly agents: LunoraAgents;` : "";
|
|
1059
1260
|
const identityTypeImport = identity ? `import type { InferIdentity } from "${base.server}";
|
|
1060
1261
|
import type * as lunoraIdentityContract from "../identity.js";
|
|
1061
1262
|
` : "";
|
|
@@ -1101,11 +1302,11 @@ import type {
|
|
|
1101
1302
|
} from "${base.server}";
|
|
1102
1303
|
|
|
1103
1304
|
import type { DataModel, DatabaseReaderFacade, DatabaseWriterFacade, Doc, Id as IdOfTable, OrmReader, OrmWriter, Relations, TableName } from "./dataModel.js";
|
|
1104
|
-
${aiTypeImport}${paymentsTypeImport}${x402TypeImport}${containersTypeImport}${workflowsTypeImport}${queuesTypeImport}${identityTypeImport}${envTypeImport}
|
|
1305
|
+
${aiTypeImport}${paymentsTypeImport}${x402TypeImport}${containersTypeImport}${workflowsTypeImport}${queuesTypeImport}${agentsTypeImport}${identityTypeImport}${envTypeImport}
|
|
1105
1306
|
export type { DataModel, Doc, Id, TableName } from "./dataModel.js";
|
|
1106
1307
|
|
|
1107
1308
|
/** Storage buckets this schema declares (\`v.storage("name")\`), narrowing \`ctx.storage.bucket(name)\`. */
|
|
1108
|
-
export type StorageBucketName = ${storageBucketUnion};${envBlock}${workflowsTypeBlock}${queuesTypeBlock}${identityTypeBlock}${envTypeBlock}
|
|
1309
|
+
export type StorageBucketName = ${storageBucketUnion};${envBlock}${workflowsTypeBlock}${queuesTypeBlock}${agentsTypeBlock}${identityTypeBlock}${envTypeBlock}
|
|
1109
1310
|
|
|
1110
1311
|
/**
|
|
1111
1312
|
* Project-typed contexts. The base contexts from \`@lunora/server\` are
|
|
@@ -1143,13 +1344,13 @@ export interface QueryCtx extends Omit<QueryCtxBase, "db" | "storage"${authOmit}
|
|
|
1143
1344
|
export interface MutationCtx extends Omit<MutationCtxBase, "db" | "storage"${workflowsOmit}${authOmit}${envOmit}> {
|
|
1144
1345
|
readonly db: Omit<DatabaseWriter, "query" | "get"> & DatabaseWriterFacade & { query: TypedTableQuery; get: TypedTableGet };
|
|
1145
1346
|
readonly orm: OrmWriter;
|
|
1146
|
-
readonly storage: ReadOnlyStorage<StorageBucketName>;${accessContextField}${kvContextField}${flagsContextField}${analyticsContextField}${envContextField}${workflowsContextField}${queuesContextField}${authContextField}
|
|
1347
|
+
readonly storage: ReadOnlyStorage<StorageBucketName>;${accessContextField}${kvContextField}${flagsContextField}${analyticsContextField}${envContextField}${workflowsContextField}${queuesContextField}${agentsContextField}${authContextField}
|
|
1147
1348
|
}
|
|
1148
1349
|
|
|
1149
1350
|
export interface ActionCtx extends Omit<ActionCtxBase, "db" | "storage"${workflowsOmit}${authOmit}${envOmit}> {
|
|
1150
1351
|
readonly db: Omit<DatabaseWriter, "query" | "get"> & DatabaseWriterFacade & { query: TypedTableQuery; get: TypedTableGet };
|
|
1151
1352
|
readonly orm: OrmWriter;
|
|
1152
|
-
readonly storage: StorageBase<StorageBucketName>;${accessContextField}${aiActionField}${paymentsActionField}${x402ActionField}${containersActionField}${kvContextField}${flagsContextField}${hyperdriveActionField}${browserActionField}${imagesActionField}${analyticsContextField}${pipelinesActionField}${r2sqlActionField}${envContextField}${workflowsContextField}${queuesContextField}${authContextField}
|
|
1353
|
+
readonly storage: StorageBase<StorageBucketName>;${accessContextField}${aiActionField}${paymentsActionField}${x402ActionField}${containersActionField}${kvContextField}${flagsContextField}${hyperdriveActionField}${browserActionField}${imagesActionField}${analyticsContextField}${pipelinesActionField}${r2sqlActionField}${envContextField}${workflowsContextField}${queuesContextField}${agentsContextField}${authContextField}
|
|
1153
1354
|
}
|
|
1154
1355
|
|
|
1155
1356
|
/**
|
|
@@ -1219,10 +1420,22 @@ const renderLifecycleManifest = (functions) => {
|
|
|
1219
1420
|
}
|
|
1220
1421
|
return manifest;
|
|
1221
1422
|
};
|
|
1222
|
-
const emitFunctions = (
|
|
1423
|
+
const emitFunctions = (options) => {
|
|
1424
|
+
const { agents = [], functions, migrations = [], mutators = [], shapes = [], useUmbrella = false, usesSandbox = false } = options;
|
|
1223
1425
|
const hasFunctions = functions.length > 0;
|
|
1224
1426
|
const base = baseSpecifiers(useUmbrella);
|
|
1225
1427
|
const { dispatchBody, importBlock, installBlock, migrationBody, mutatorPaths, shapeBody } = renderFunctionRegistry(functions, migrations, mutators, shapes);
|
|
1428
|
+
const agentRegistry = renderAgentFunctionRegistry(agents, functions);
|
|
1429
|
+
const sandboxRegistry = renderSandboxFunctionRegistry(usesSandbox, functions);
|
|
1430
|
+
const autoLines = [agentRegistry.lines, sandboxRegistry.lines].filter((block) => block.length > 0).join("\n");
|
|
1431
|
+
let dispatchBodyWithAgents = dispatchBody;
|
|
1432
|
+
if (autoLines.length > 0) {
|
|
1433
|
+
dispatchBodyWithAgents = dispatchBody.length > 0 ? `${dispatchBody.trimEnd()}
|
|
1434
|
+
${autoLines}
|
|
1435
|
+
` : `
|
|
1436
|
+
${autoLines}
|
|
1437
|
+
`;
|
|
1438
|
+
}
|
|
1226
1439
|
const lifecycleHooks = renderLifecycleManifest(functions);
|
|
1227
1440
|
const shapeTypeImport = shapes.length > 0 ? `import type { RegisteredShape } from "${base.server}";
|
|
1228
1441
|
` : "";
|
|
@@ -1267,7 +1480,7 @@ ${caller.implementation}
|
|
|
1267
1480
|
const callRegisteredHelper = hasFunctions ? `${CALL_REGISTERED_HELPER}
|
|
1268
1481
|
|
|
1269
1482
|
` : "";
|
|
1270
|
-
return `${GENERATED_HEADER}${importBlock}${compiledArgsImport}${shapeTypeImport}import { LunoraError } from "${base.server}";
|
|
1483
|
+
return `${GENERATED_HEADER}${importBlock}${agentRegistry.importLine}${sandboxRegistry.importLine}${compiledArgsImport}${shapeTypeImport}import { LunoraError } from "${base.server}";
|
|
1271
1484
|
import type { ActionCtx, MutationCtx, QueryCtx } from "./server.js";
|
|
1272
1485
|
${dataModelImport}
|
|
1273
1486
|
/**
|
|
@@ -1288,12 +1501,12 @@ export interface RegisteredLunoraFunction {
|
|
|
1288
1501
|
/** \`"internal"\` functions are rejected on the external RPC path; absence === public. */
|
|
1289
1502
|
visibility?: "internal" | "public";
|
|
1290
1503
|
}
|
|
1291
|
-
|
|
1504
|
+
${agentRegistry.prelude}${sandboxRegistry.prelude}
|
|
1292
1505
|
/**
|
|
1293
1506
|
* Static dispatch table. The key matches the \`__lunoraRef\` the client
|
|
1294
1507
|
* emits (\`api[namespace][fn].__lunoraRef === "namespace:fn"\`).
|
|
1295
1508
|
*/
|
|
1296
|
-
export const LUNORA_FUNCTIONS: Record<string, RegisteredLunoraFunction> = {${
|
|
1509
|
+
export const LUNORA_FUNCTIONS: Record<string, RegisteredLunoraFunction> = {${dispatchBodyWithAgents}};
|
|
1297
1510
|
${compiledArgsInstall}${shapeRegistry}${mutatorPathsRegistry}
|
|
1298
1511
|
/**
|
|
1299
1512
|
* Connection-lifecycle manifest: the function paths the generated ShardDO
|
|
@@ -1967,6 +2180,62 @@ type WorkflowParamsOf<Definition> = Definition extends { __params?: infer Params
|
|
|
1967
2180
|
/** Output type carried by a \`defineWorkflow\` definition (its phantom \`__output\`), so each entrypoint keeps the authored return type. */
|
|
1968
2181
|
type WorkflowOutputOf<Definition> = Definition extends { __output?: infer Output } ? Output : unknown;
|
|
1969
2182
|
|
|
2183
|
+
${classes}`;
|
|
2184
|
+
};
|
|
2185
|
+
const emitAgents = (agents) => {
|
|
2186
|
+
if (agents.length === 0) {
|
|
2187
|
+
return "";
|
|
2188
|
+
}
|
|
2189
|
+
const voiceAgents = agents.filter((agent) => agent.voice);
|
|
2190
|
+
const hasVoice = voiceAgents.length > 0;
|
|
2191
|
+
const classes = agents.map((agent) => {
|
|
2192
|
+
assertIdentifier(agent.exportName, `agent export "${agent.exportName}"`);
|
|
2193
|
+
assertIdentifier(agent.className, `agent class "${agent.className}"`);
|
|
2194
|
+
const workflowClass = `/** WorkflowEntrypoint for the \`${agent.exportName}\` agent (binding \`${agent.bindingName}\`). */
|
|
2195
|
+
export class ${agent.className} extends LunoraWorkflow<AgentRunInput, AgentRunResult> {
|
|
2196
|
+
public constructor(ctx: ConstructorParameters<typeof LunoraWorkflow>[0], env: Record<string, unknown>) {
|
|
2197
|
+
super(ctx, env, compileAgentWorkflow(${agent.exportName}, "${agent.exportName}"), "${agent.exportName}");
|
|
2198
|
+
}
|
|
2199
|
+
}
|
|
2200
|
+
`;
|
|
2201
|
+
if (!agent.voice) {
|
|
2202
|
+
return workflowClass;
|
|
2203
|
+
}
|
|
2204
|
+
const voiceClassName = agent.voiceClassName ?? "";
|
|
2205
|
+
const voiceBindingName = agent.voiceBindingName ?? "";
|
|
2206
|
+
assertIdentifier(voiceClassName, `agent voice class "${voiceClassName}"`);
|
|
2207
|
+
const voiceClass = `
|
|
2208
|
+
/** Voice-session Durable Object for the \`${agent.exportName}\` agent (binding \`${voiceBindingName}\`). */
|
|
2209
|
+
export class ${voiceClassName} extends VoiceSessionDO {
|
|
2210
|
+
public constructor(ctx: ConstructorParameters<typeof VoiceSessionDO>[0], env: Record<string, unknown>) {
|
|
2211
|
+
super(ctx, env, ${agent.exportName}, "${agent.exportName}");
|
|
2212
|
+
}
|
|
2213
|
+
}
|
|
2214
|
+
`;
|
|
2215
|
+
return `${workflowClass}${voiceClass}`;
|
|
2216
|
+
}).join("\n");
|
|
2217
|
+
const imports = agents.map((agent) => agent.exportName).join(", ");
|
|
2218
|
+
const runtimeImport = hasVoice ? `import { compileAgentWorkflow, VoiceSessionDO } from "@lunora/agent";` : `import { compileAgentWorkflow } from "@lunora/agent";`;
|
|
2219
|
+
const voiceHeaderNote = hasVoice ? `
|
|
2220
|
+
*
|
|
2221
|
+
* Voice-enabled agents ALSO get a \`VoiceSessionDO\` subclass here — a real
|
|
2222
|
+
* Durable Object (unlike the Workflow), so wrangler needs both its
|
|
2223
|
+
* \`durable_objects\` binding and its \`class_name\` export (the same re-export
|
|
2224
|
+
* line covers it).` : "";
|
|
2225
|
+
return `${GENERATED_HEADER}/**
|
|
2226
|
+
* WorkflowEntrypoint classes for the agents declared in \`lunora/agents.ts\`.
|
|
2227
|
+
* Each \`defineAgent\` compiles a replay-safe tool-loop onto a Cloudflare
|
|
2228
|
+
* Workflow. Re-export them from your worker entry — wrangler requires each
|
|
2229
|
+
* \`workflows[].class_name\` to be exported by the worker:
|
|
2230
|
+
*
|
|
2231
|
+
* \`export * from "./lunora/_generated/agents.js";\`${voiceHeaderNote}
|
|
2232
|
+
*/
|
|
2233
|
+
import LunoraWorkflow from "@lunora/workflow/do";
|
|
2234
|
+
${runtimeImport}
|
|
2235
|
+
import type { AgentRunInput, AgentRunResult } from "@lunora/agent";
|
|
2236
|
+
|
|
2237
|
+
import { ${imports} } from "../agents.js";
|
|
2238
|
+
|
|
1970
2239
|
${classes}`;
|
|
1971
2240
|
};
|
|
1972
2241
|
const emitQueues = (queues) => {
|
|
@@ -2045,6 +2314,31 @@ ${specEntries}
|
|
|
2045
2314
|
`
|
|
2046
2315
|
};
|
|
2047
2316
|
};
|
|
2317
|
+
const emitAgentFragments = (agents) => {
|
|
2318
|
+
if (agents.length === 0) {
|
|
2319
|
+
return { build: "", contextField: "", importLines: [], specs: "" };
|
|
2320
|
+
}
|
|
2321
|
+
for (const agent of agents) {
|
|
2322
|
+
assertIdentifier(agent.exportName, `agent export "${agent.exportName}"`);
|
|
2323
|
+
assertIdentifier(agent.bindingName, `agent binding "${agent.bindingName}"`);
|
|
2324
|
+
}
|
|
2325
|
+
const specEntries = agents.map((agent) => ` { binding: "${agent.bindingName}", exportName: "${agent.exportName}"${agent.publicRun === true ? ", publicRun: true" : ""} },`).join("\n");
|
|
2326
|
+
return {
|
|
2327
|
+
build: `
|
|
2328
|
+
const agents = createAgentContext(env, LUNORA_AGENTS);
|
|
2329
|
+
`,
|
|
2330
|
+
contextField: `
|
|
2331
|
+
agents,`,
|
|
2332
|
+
importLines: [`import { createAgentContext } from "@lunora/agent";`, `import type { AgentBindingSpec } from "@lunora/agent";`],
|
|
2333
|
+
// eslint-disable-next-line no-secrets/no-secrets -- the emitted readonly-array type annotation is dense generated TS, not a credential
|
|
2334
|
+
specs: `
|
|
2335
|
+
/** Wiring specs for \`ctx.agents\` (codegen-derived from \`lunora/agents.ts\`). */
|
|
2336
|
+
const LUNORA_AGENTS: ReadonlyArray<AgentBindingSpec> = [
|
|
2337
|
+
${specEntries}
|
|
2338
|
+
];
|
|
2339
|
+
`
|
|
2340
|
+
};
|
|
2341
|
+
};
|
|
2048
2342
|
const emitWorkflowsMetadataFragments = (workflows) => {
|
|
2049
2343
|
if (workflows.length === 0) {
|
|
2050
2344
|
return { constant: "", override: "" };
|
|
@@ -2208,6 +2502,7 @@ const buildDoTypeImports = (hasVectors, hasWorkflows, hasQueues, hasFlags) => [
|
|
|
2208
2502
|
];
|
|
2209
2503
|
const emitShard = ({
|
|
2210
2504
|
advisories = [],
|
|
2505
|
+
agents = [],
|
|
2211
2506
|
containers = [],
|
|
2212
2507
|
env,
|
|
2213
2508
|
flagKeys = [],
|
|
@@ -2262,6 +2557,7 @@ const emitShard = ({
|
|
|
2262
2557
|
importLines: workflowImportLines,
|
|
2263
2558
|
specs: workflowSpecs
|
|
2264
2559
|
} = emitWorkflowFragments(workflows);
|
|
2560
|
+
const { build: agentsBuild, contextField: agentsContextField, importLines: agentImportLines, specs: agentSpecs } = emitAgentFragments(agents);
|
|
2265
2561
|
const {
|
|
2266
2562
|
build: paymentsBuild,
|
|
2267
2563
|
configField: paymentsConfigField,
|
|
@@ -2408,6 +2704,7 @@ const LUNORA_RLS_READ_REGISTRY = buildRlsReadRegistry(Object.values(LUNORA_FUNCT
|
|
|
2408
2704
|
...containerImportLines,
|
|
2409
2705
|
...workflowImportLines,
|
|
2410
2706
|
...queueImportLines,
|
|
2707
|
+
...agentImportLines,
|
|
2411
2708
|
...paymentsImports,
|
|
2412
2709
|
...x402Imports,
|
|
2413
2710
|
``,
|
|
@@ -2749,7 +3046,7 @@ const LUNORA_STORAGE_RULES: StorageRulesResult = ${JSON.stringify(storageRulesDa
|
|
|
2749
3046
|
|
|
2750
3047
|
/** Which optional package-backed features this app wires up (discovered from imports / \`ctx.*\` reads / schema signals) served via \`__lunora_admin__:studioFeatures\` so the studio hides nav pages whose package isn't enabled. */
|
|
2751
3048
|
const LUNORA_STUDIO_FEATURES: StudioFeaturesResult = ${JSON.stringify(studioFeaturesData, void 0, 4)};
|
|
2752
|
-
${flagsOverrides.constant}${shapeReadRegistryConst}${workflowsMetadataConst}${queuesMetadataConst}${containerSpecs}${workflowSpecs}${queueSpecs}
|
|
3049
|
+
${flagsOverrides.constant}${shapeReadRegistryConst}${workflowsMetadataConst}${queuesMetadataConst}${containerSpecs}${workflowSpecs}${queueSpecs}${agentSpecs}
|
|
2753
3050
|
export interface ShardDOConfig {
|
|
2754
3051
|
/** Opt into change-data-capture: records a post-image to \`__cdc_log\` on every write (backs streaming export + replay-PITR). */
|
|
2755
3052
|
cdc?: boolean;
|
|
@@ -3165,7 +3462,7 @@ ${flagsOverrides.evaluateOverride}${flagsOverrides.subscriptionOverride}${workfl
|
|
|
3165
3462
|
// dispatch path) fall back to the per-request fields as before.
|
|
3166
3463
|
const userId = options.identity ? options.identity.userId : this.getCurrentUserId();
|
|
3167
3464
|
const identity = options.identity ? options.identity.identity : this.getCurrentIdentity();
|
|
3168
|
-
${vectorsBuild}${aiBuild}${everyContextBuild}${containersBuild}${workflowsBuild}${queuesBuild}
|
|
3465
|
+
${vectorsBuild}${aiBuild}${everyContextBuild}${containersBuild}${workflowsBuild}${queuesBuild}${agentsBuild}
|
|
3169
3466
|
const scheduler = (config.scheduler?.(env) ?? schedulerStub) as SchedulerLike;
|
|
3170
3467
|
// Build the storage adapter once and share it between \`ctx.storage\`
|
|
3171
3468
|
// and \`ctx.db.system._storage\` so both read the same R2 binding. The
|
|
@@ -3207,7 +3504,7 @@ ${facadeBlock}${paymentsBuild}
|
|
|
3207
3504
|
log,
|
|
3208
3505
|
now,${ormContextField}
|
|
3209
3506
|
scheduler,
|
|
3210
|
-
storage,${vectorsContextField}${aiContextField}${everyContextField}${paymentsContextField}${containersContextField}${workflowsContextField}${queuesContextField}
|
|
3507
|
+
storage,${vectorsContextField}${aiContextField}${everyContextField}${paymentsContextField}${containersContextField}${workflowsContextField}${queuesContextField}${agentsContextField}
|
|
3211
3508
|
};
|
|
3212
3509
|
${isActionLine}${actionOnlyBlock}
|
|
3213
3510
|
ctx.runAction = (reference: FunctionReference, fnArgs: Record<string, unknown>) => dispatchRun("action", reference.__lunoraRef, fnArgs, ctx);
|
|
@@ -3471,4 +3768,4 @@ const emitWranglerCronTriggers = (crons) => {
|
|
|
3471
3768
|
return triggers;
|
|
3472
3769
|
};
|
|
3473
3770
|
|
|
3474
|
-
export { APP_METHOD_CAPABILITIES as A, CAPABILITIES as C, GENERATED_HEADER as G,
|
|
3771
|
+
export { APP_METHOD_CAPABILITIES as A, CAPABILITIES as C, GENERATED_HEADER as G, emitApi as a, emitCollections as b, emitContainers as c, emitCrons as d, emitAgents as e, emitDataModel as f, emitDrizzleSchema as g, emitFunctions as h, emitServer as i, emitShard as j, emitVectors as k, emitWorkflows as l, emitWranglerCronTriggers as m, buildStorageColumns as n, emitQueues as o, emitSeed as p };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { A as APP_METHOD_CAPABILITIES, G as GENERATED_HEADER } from './emit-
|
|
1
|
+
import { A as APP_METHOD_CAPABILITIES, G as GENERATED_HEADER } from './emit-C_29WVlW.mjs';
|
|
2
2
|
|
|
3
3
|
const hasFlagKey = (key) => `has${key.charAt(0).toUpperCase()}${key.slice(1)}`;
|
|
4
4
|
const LONG_TAIL = APP_METHOD_CAPABILITIES.map(
|
|
@@ -11,6 +11,9 @@ const buildAccessImports = (hasAccess, hasAuth) => hasAccess ? [
|
|
|
11
11
|
`import { createAccessResolver${hasAuth ? ", composeResolvers" : ""} } from "@lunora/cloudflare-access";`
|
|
12
12
|
] : [];
|
|
13
13
|
const buildKvImports = (hasKv) => hasKv ? [`import { createKvIntrospectorFromEnv } from "@lunora/bindings/kv";`] : [];
|
|
14
|
+
const hasEmailAgents = (options) => (options.emailAgents?.length ?? 0) > 0;
|
|
15
|
+
const buildInboundImports = (options) => hasEmailAgents(options) ? [`import { dispatchAgentEmail } from "@lunora/agent/inbound";`] : [];
|
|
16
|
+
const buildAgentDefinitionsImport = (options) => hasEmailAgents(options) ? [`import * as lunoraAgentDefinitions from "../agents.js";`] : [];
|
|
14
17
|
const buildImportLines = (options) => {
|
|
15
18
|
const {
|
|
16
19
|
hasAccess,
|
|
@@ -59,10 +62,12 @@ const buildImportLines = (options) => {
|
|
|
59
62
|
...hasScheduler ? [`import type { DurableObjectNamespaceLike } from "@lunora/scheduler";`, `import { createScheduler } from "@lunora/scheduler";`] : [],
|
|
60
63
|
...hasStorage ? [`import type { R2BucketLike, Storage } from "@lunora/storage";`, `import { createBucketStorage, createStorage } from "@lunora/storage";`] : [],
|
|
61
64
|
...hasWorkflow ? [`import { createWorkflowsRestClient } from "@lunora/workflow";`] : [],
|
|
65
|
+
...buildInboundImports(options),
|
|
62
66
|
`import type { ${[...runtimeTypeImports].toSorted((a, b) => a.localeCompare(b)).join(", ")} } from "${runtimeModule}";`,
|
|
63
67
|
`import { ${runtimeValueImports} } from "${runtimeModule}";`,
|
|
64
68
|
``,
|
|
65
69
|
...buildIdentityImports(options.identity),
|
|
70
|
+
...buildAgentDefinitionsImport(options),
|
|
66
71
|
...hasGlobal || hasHyperdriveGlobal ? [`import schema from "../schema.js";`] : [],
|
|
67
72
|
`import { LUNORA_CRONS } from "./crons.js";`,
|
|
68
73
|
`import { LUNORA_FUNCTIONS } from "./functions.js";`,
|
|
@@ -383,6 +388,18 @@ const buildWorkerOptionLines = (options) => [
|
|
|
383
388
|
}` : ` if (this.accessSelector) {
|
|
384
389
|
options.resolveIdentity = createAccessResolver(this.accessSelector(env));
|
|
385
390
|
}`
|
|
391
|
+
] : [],
|
|
392
|
+
// Voice-enabled agents: map each export name to its `VOICE_*` Durable Object
|
|
393
|
+
// namespace so the runtime serves `/_lunora/voice/<exportName>`. Read off
|
|
394
|
+
// `env` structurally (the binding is provisioned by the config layer's
|
|
395
|
+
// reconcile step, so it may not be on the generated `Env` type). Emitted only
|
|
396
|
+
// when at least one agent opted into voice — voice-free output is unchanged.
|
|
397
|
+
...options.voiceAgents && options.voiceAgents.length > 0 ? [
|
|
398
|
+
` options.voiceAgents = {
|
|
399
|
+
${options.voiceAgents.map(
|
|
400
|
+
(agent) => ` ${JSON.stringify(agent.exportName)}: (env as Record<string, unknown>)[${JSON.stringify(agent.bindingName)}] as ShardNamespaceLike,`
|
|
401
|
+
).join("\n")}
|
|
402
|
+
};`
|
|
386
403
|
] : []
|
|
387
404
|
];
|
|
388
405
|
const buildBaseWorkerOptions = (options) => [
|
|
@@ -554,6 +571,12 @@ const emitApp = (options) => {
|
|
|
554
571
|
const buildWorkerLine = options.hasFramework ? ` const buildWorker = (env: Env): LunoraWorker =>
|
|
555
572
|
host ? withFrameworkWorker(host, (hostEnv) => this.buildWorkerOptions(hostEnv as Env, ${getAuthArgument})) : createWorker(this.buildWorkerOptions(env, ${getAuthArgument}));` : ` const buildWorker = (env: Env): LunoraWorker => createWorker(this.buildWorkerOptions(env, ${getAuthArgument}));`;
|
|
556
573
|
const assembleParameter = options.hasFramework ? `host?: FrameworkHostHandler` : ``;
|
|
574
|
+
const emailAgents = options.emailAgents ?? [];
|
|
575
|
+
const emailAgentsBlock = emailAgents.length > 0 ? ` composed.email = dispatchAgentEmail([
|
|
576
|
+
${emailAgents.map((agent) => ` { agent: lunoraAgentDefinitions.${agent.exportName}, binding: ${JSON.stringify(agent.bindingName)} },`).join("\n")}
|
|
577
|
+
]);
|
|
578
|
+
|
|
579
|
+
` : "";
|
|
557
580
|
const buildTerminals = ` /** Materialise the standalone Cloudflare worker + \`ShardDO\` class. */
|
|
558
581
|
public build(): ComposedApp {
|
|
559
582
|
return this.assemble();
|
|
@@ -630,7 +653,7 @@ ${buildWorkerLine}
|
|
|
630
653
|
},` : ""}
|
|
631
654
|
};
|
|
632
655
|
|
|
633
|
-
if (this.emailHandler) {
|
|
656
|
+
${emailAgentsBlock} if (this.emailHandler) {
|
|
634
657
|
const handler = this.emailHandler;
|
|
635
658
|
|
|
636
659
|
composed.email = (message, rawEnv, context) => handler(rawEnv as Env)(message, rawEnv, context);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@lunora/codegen",
|
|
3
|
-
"version": "1.0.0-alpha.
|
|
3
|
+
"version": "1.0.0-alpha.44",
|
|
4
4
|
"description": "Code generator for Lunora: emits _generated/{api,server,dataModel}.ts from your schema",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"cloudflare",
|
|
@@ -46,13 +46,14 @@
|
|
|
46
46
|
"access": "public"
|
|
47
47
|
},
|
|
48
48
|
"dependencies": {
|
|
49
|
-
"@lunora/advisor": "1.0.0-alpha.
|
|
50
|
-
"@lunora/
|
|
51
|
-
"@lunora/
|
|
52
|
-
"@lunora/
|
|
53
|
-
"@lunora/
|
|
54
|
-
"@lunora/
|
|
55
|
-
"@lunora/
|
|
49
|
+
"@lunora/advisor": "1.0.0-alpha.28",
|
|
50
|
+
"@lunora/agent": "1.0.0-alpha.2",
|
|
51
|
+
"@lunora/container": "1.0.0-alpha.12",
|
|
52
|
+
"@lunora/errors": "1.0.0-alpha.5",
|
|
53
|
+
"@lunora/queue": "1.0.0-alpha.8",
|
|
54
|
+
"@lunora/scheduler": "1.0.0-alpha.10",
|
|
55
|
+
"@lunora/values": "1.0.0-alpha.8",
|
|
56
|
+
"@lunora/workflow": "1.0.0-alpha.10",
|
|
56
57
|
"ts-morph": "^28.0.0"
|
|
57
58
|
},
|
|
58
59
|
"engines": {
|
|
@@ -1,3 +0,0 @@
|
|
|
1
|
-
import '@lunora/errors';
|
|
2
|
-
export { G as GENERATED_HEADER, m as buildStorageColumns, e as emitApi, a as emitCollections, b as emitContainers, c as emitCrons, d as emitDataModel, f as emitDrizzleSchema, g as emitFunctions, n as emitQueues, o as emitSeed, h as emitServer, i as emitShard, j as emitVectors, k as emitWorkflows, l as emitWranglerCronTriggers } from './emit-31Yg1Ee5.mjs';
|
|
3
|
-
import './paths-BRd6JHuF.mjs';
|