@autobe/agent 0.3.22 → 0.3.24

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.
Files changed (28) hide show
  1. package/lib/constants/AutoBeSystemPromptConstant.d.ts +1 -0
  2. package/lib/constants/AutoBeSystemPromptConstant.js.map +1 -1
  3. package/lib/index.mjs +453 -149
  4. package/lib/index.mjs.map +1 -1
  5. package/lib/orchestrate/interface/orchestrateInterface.js +5 -4
  6. package/lib/orchestrate/interface/orchestrateInterface.js.map +1 -1
  7. package/lib/orchestrate/interface/orchestrateInterfaceComplement.d.ts +4 -0
  8. package/lib/orchestrate/interface/orchestrateInterfaceComplement.js +482 -0
  9. package/lib/orchestrate/interface/orchestrateInterfaceComplement.js.map +1 -0
  10. package/lib/orchestrate/interface/orchestrateInterfaceComponents.js +3 -109
  11. package/lib/orchestrate/interface/orchestrateInterfaceComponents.js.map +1 -1
  12. package/lib/orchestrate/interface/orchestrateInterfaceEndpoints.js +5 -8
  13. package/lib/orchestrate/interface/orchestrateInterfaceEndpoints.js.map +1 -1
  14. package/lib/orchestrate/interface/orchestrateInterfaceOperations.js +5 -8
  15. package/lib/orchestrate/interface/orchestrateInterfaceOperations.js.map +1 -1
  16. package/lib/orchestrate/interface/transformInterfaceHistories.js +2 -0
  17. package/lib/orchestrate/interface/transformInterfaceHistories.js.map +1 -1
  18. package/lib/orchestrate/prisma/orchestratePrismaCompiler.js +2 -1
  19. package/lib/orchestrate/prisma/orchestratePrismaCompiler.js.map +1 -1
  20. package/package.json +4 -4
  21. package/src/constants/AutoBeSystemPromptConstant.ts +1 -0
  22. package/src/orchestrate/interface/orchestrateInterface.ts +6 -6
  23. package/src/orchestrate/interface/orchestrateInterfaceComplement.ts +235 -0
  24. package/src/orchestrate/interface/orchestrateInterfaceComponents.ts +19 -57
  25. package/src/orchestrate/interface/orchestrateInterfaceEndpoints.ts +4 -7
  26. package/src/orchestrate/interface/orchestrateInterfaceOperations.ts +4 -7
  27. package/src/orchestrate/interface/transformInterfaceHistories.ts +2 -0
  28. package/src/orchestrate/prisma/orchestratePrismaCompiler.ts +3 -1
@@ -0,0 +1,235 @@
1
+ import { IAgenticaController, MicroAgentica } from "@agentica/core";
2
+ import { AutoBeOpenApi } from "@autobe/interface";
3
+ import {
4
+ ILlmApplication,
5
+ ILlmSchema,
6
+ OpenApiTypeChecker,
7
+ } from "@samchon/openapi";
8
+ import { OpenApiV3_1Emender } from "@samchon/openapi/lib/converters/OpenApiV3_1Emender";
9
+ import { IPointer } from "tstl";
10
+ import typia from "typia";
11
+
12
+ import { AutoBeSystemPromptConstant } from "../../constants/AutoBeSystemPromptConstant";
13
+ import { AutoBeContext } from "../../context/AutoBeContext";
14
+ import { assertSchemaModel } from "../../context/assertSchemaModel";
15
+ import { transformInterfaceHistories } from "./transformInterfaceHistories";
16
+
17
+ export function orchestrateInterfaceComplement<Model extends ILlmSchema.Model>(
18
+ ctx: AutoBeContext<Model>,
19
+ document: AutoBeOpenApi.IDocument,
20
+ retry: number = 8,
21
+ ): Promise<AutoBeOpenApi.IComponents> {
22
+ return step(ctx, document, retry);
23
+ }
24
+
25
+ async function step<Model extends ILlmSchema.Model>(
26
+ ctx: AutoBeContext<Model>,
27
+ document: AutoBeOpenApi.IDocument,
28
+ retry: number,
29
+ ): Promise<AutoBeOpenApi.IComponents> {
30
+ const missed: string[] = getMissed(document);
31
+ if (missed.length === 0 || retry <= 0) return document.components;
32
+
33
+ const pointer: IPointer<Record<
34
+ string,
35
+ AutoBeOpenApi.IJsonSchemaDescriptive
36
+ > | null> = {
37
+ value: null,
38
+ };
39
+ const agentica: MicroAgentica<Model> = new MicroAgentica({
40
+ model: ctx.model,
41
+ vendor: ctx.vendor,
42
+ config: {
43
+ ...(ctx.config ?? {}),
44
+ executor: {
45
+ describe: null,
46
+ },
47
+ },
48
+ histories: [
49
+ ...transformInterfaceHistories(
50
+ ctx.state(),
51
+ AutoBeSystemPromptConstant.INTERFACE_COMPLEMENT,
52
+ ),
53
+ {
54
+ type: "assistantMessage",
55
+ text: [
56
+ "Here is the OpenAPI document what you've made:",
57
+ "",
58
+ "```json",
59
+ JSON.stringify(document),
60
+ "```",
61
+ ].join("\n"),
62
+ },
63
+ {
64
+ type: "assistantMessage",
65
+ text: [
66
+ "You have missed below schema types in the document.components.schemas:",
67
+ "",
68
+ ...missed.map((s) => `- ${s}`),
69
+ ].join("\n"),
70
+ },
71
+ ],
72
+ tokenUsage: ctx.usage(),
73
+ controllers: [
74
+ createApplication({
75
+ model: ctx.model,
76
+ build: (next) => {
77
+ pointer.value = (OpenApiV3_1Emender.convertComponents({
78
+ schemas: next,
79
+ }).schemas ?? {}) as Record<
80
+ string,
81
+ AutoBeOpenApi.IJsonSchemaDescriptive
82
+ >;
83
+ },
84
+ }),
85
+ ],
86
+ });
87
+ agentica.on("request", async (event) => {
88
+ event.body.tool_choice = "required";
89
+ });
90
+
91
+ await agentica.conversate("Fill missing schema types please");
92
+ if (pointer.value === null) {
93
+ // unreachable
94
+ throw new Error(
95
+ "Failed to fill missing schema types. No response from agentica.",
96
+ );
97
+ }
98
+ ctx.dispatch({
99
+ type: "interfaceComplement",
100
+ missed,
101
+ schemas: pointer.value,
102
+ step: ctx.state().analyze?.step ?? 0,
103
+ created_at: new Date().toISOString(),
104
+ });
105
+
106
+ const newComponents: AutoBeOpenApi.IComponents = {
107
+ schemas: {
108
+ ...pointer.value,
109
+ ...document.components.schemas,
110
+ },
111
+ authorization: document.components.authorization,
112
+ };
113
+ return step(
114
+ ctx,
115
+ {
116
+ ...document,
117
+ components: newComponents,
118
+ },
119
+ retry - 1,
120
+ );
121
+ }
122
+
123
+ const getMissed = (document: AutoBeOpenApi.IDocument): string[] => {
124
+ const missed: Set<string> = new Set();
125
+ const check = (name: string) => {
126
+ if (document.components.schemas[name] === undefined) missed.add(name);
127
+ };
128
+ for (const op of document.operations) {
129
+ if (op.requestBody !== null) check(op.requestBody.typeName);
130
+ if (op.responseBody !== null) check(op.responseBody.typeName);
131
+ }
132
+ for (const value of Object.values(document.components.schemas))
133
+ OpenApiTypeChecker.visit({
134
+ components: document.components,
135
+ schema: value,
136
+ closure: (next) => {
137
+ if (OpenApiTypeChecker.isReference(next))
138
+ check(next.$ref.split("/").pop()!);
139
+ },
140
+ });
141
+ return Array.from(missed);
142
+ };
143
+
144
+ function createApplication<Model extends ILlmSchema.Model>(props: {
145
+ model: Model;
146
+ build: (
147
+ schemas: Record<string, AutoBeOpenApi.IJsonSchemaDescriptive>,
148
+ ) => void;
149
+ }): IAgenticaController.IClass<Model> {
150
+ assertSchemaModel(props.model);
151
+ const application: ILlmApplication<Model> = collection[
152
+ props.model
153
+ ] as unknown as ILlmApplication<Model>;
154
+ return {
155
+ protocol: "class",
156
+ name: "interface",
157
+ application,
158
+ execute: {
159
+ complementComponents: (next) => {
160
+ props.build(next.schemas);
161
+ },
162
+ } satisfies IApplication,
163
+ };
164
+ }
165
+
166
+ const claude = typia.llm.application<
167
+ IApplication,
168
+ "claude",
169
+ { reference: true }
170
+ >();
171
+ const collection = {
172
+ chatgpt: typia.llm.application<
173
+ IApplication,
174
+ "chatgpt",
175
+ { reference: true }
176
+ >(),
177
+ claude,
178
+ llama: claude,
179
+ deepseek: claude,
180
+ "3.1": claude,
181
+ "3.0": typia.llm.application<IApplication, "3.0">(),
182
+ };
183
+
184
+ interface IApplication {
185
+ /**
186
+ * Complements missing schema types
187
+ *
188
+ * This method fills in schema definitions that are referenced via $ref but
189
+ * not yet defined in the `components.schemas` section. For example, if an API
190
+ * operation references `{ "$ref": "#/components/schemas/UserProfile" }` but
191
+ * `UserProfile` type is not defined in `components.schemas`, this method will
192
+ * add the missing schema definition.
193
+ *
194
+ * This function is designed to be called via AI function calling mechanism to
195
+ * ensure the OpenAPI document is complete and all referenced schemas are
196
+ * properly defined.
197
+ */
198
+ complementComponents(props: IComplementComponentsProps): void;
199
+ }
200
+ interface IComplementComponentsProps {
201
+ /**
202
+ * A collection of missing schema definitions that need to be added to the
203
+ * OpenAPI document's `components.schemas` section.
204
+ *
205
+ * This object contains schema definitions for types that are referenced but
206
+ * not yet defined:
207
+ *
208
+ * - Key: Schema name (`string`): The name of the schema type that will be
209
+ * referenced in $ref statements
210
+ * - Value: `AutoBeOpenApi.IJsonSchema` - The complete JSON Schema definition
211
+ * for that type
212
+ *
213
+ * Example structure:
214
+ *
215
+ * ```typescript
216
+ * {
217
+ * "UserProfile": {
218
+ * "type": "object",
219
+ * "properties": {
220
+ * "id": { "type": "string" },
221
+ * "name": { "type": "string" },
222
+ * "email": { "type": "string", "format": "email" }
223
+ * },
224
+ * "required": ["id", "name", "email"]
225
+ * }
226
+ * }
227
+ * ```
228
+ *
229
+ * Each schema definition follows the JSON Schema specification and will be
230
+ * directly inserted into the OpenAPI document's components.schemas section,
231
+ * making them available for $ref references throughout the API
232
+ * specification.
233
+ */
234
+ schemas: Record<string, AutoBeOpenApi.IJsonSchemaDescriptive>;
235
+ }
@@ -1,11 +1,6 @@
1
1
  import { IAgenticaController, MicroAgentica } from "@agentica/core";
2
2
  import { AutoBeOpenApi } from "@autobe/interface";
3
- import {
4
- ILlmApplication,
5
- ILlmSchema,
6
- IValidation,
7
- OpenApiTypeChecker,
8
- } from "@samchon/openapi";
3
+ import { ILlmApplication, ILlmSchema } from "@samchon/openapi";
9
4
  import { OpenApiV3_1Emender } from "@samchon/openapi/lib/converters/OpenApiV3_1Emender";
10
5
  import { IPointer } from "tstl";
11
6
  import typia from "typia";
@@ -184,40 +179,6 @@ function createApplication<Model extends ILlmSchema.Model>(props: {
184
179
  const application: ILlmApplication<Model> = collection[
185
180
  props.model
186
181
  ] as unknown as ILlmApplication<Model>;
187
- const validate = (next: unknown): IValidation => {
188
- const result: IValidation<IMakeComponentsProps> =
189
- typia.validate<IMakeComponentsProps>(next);
190
- if (result.success === false) return result;
191
- props.pointer.value = result.data.components;
192
-
193
- const errors: IValidation.IError[] = [];
194
- for (const value of Object.values(result.data.components.schemas)) {
195
- OpenApiTypeChecker.visit({
196
- components: result.data.components,
197
- schema: value,
198
- closure: (v) => {
199
- if (OpenApiTypeChecker.isReference(v)) {
200
- const key: string = v.$ref.split("/").at(-1)!;
201
- if (result.data.components.schemas?.[key] === undefined)
202
- errors.push({
203
- path: `components.schemas.${key}`,
204
- expected: "AutoBeOpenApi.IJsonSchemaDescriptive",
205
- value: "undefined",
206
- });
207
- }
208
- },
209
- });
210
- }
211
- if (errors.length !== 0)
212
- return {
213
- success: false,
214
- data: result.data,
215
- errors,
216
- };
217
- return result;
218
- };
219
-
220
- application.functions[0].validate = validate;
221
182
  return {
222
183
  protocol: "class",
223
184
  name: "interface",
@@ -225,9 +186,6 @@ function createApplication<Model extends ILlmSchema.Model>(props: {
225
186
  execute: {
226
187
  makeComponents: async (next) => {
227
188
  await props.build(next.components);
228
- return {
229
- success: true,
230
- };
231
189
  },
232
190
  } satisfies IApplication,
233
191
  };
@@ -303,22 +261,26 @@ interface IMakeComponentsProps {
303
261
  *
304
262
  * Example structure:
305
263
  *
306
- * components: {
307
- * schemas: {
308
- * IUser: {
309
- * type: "object",
310
- * properties: {
311
- * id: { type: "string", format: "uuid" },
312
- * email: { type: "string", format: "email" },
313
- * profile: { "$ref": "#/components/schemas/IUserProfile" }
314
- * },
315
- * required: ["id", "email"],
316
- * description: "User entity representing system account holders..."
264
+ * ```typescript
265
+ * {
266
+ * components: {
267
+ * schemas: {
268
+ * IUser: {
269
+ * type: "object",
270
+ * properties: {
271
+ * id: { type: "string", format: "uuid" },
272
+ * email: { type: "string", format: "email" },
273
+ * profile: { "$ref": "#/components/schemas/IUserProfile" }
317
274
  * },
318
- * "IUser.ICreate": { ... },
319
- * // Additional schemas
320
- * }
275
+ * required: ["id", "email"],
276
+ * description: "User entity representing system account holders..."
277
+ * },
278
+ * "IUser.ICreate": { ... },
279
+ * // Additional schemas
321
280
  * }
281
+ * }
282
+ * }
283
+ * ```
322
284
  */
323
285
  components: AutoBeOpenApi.IComponents;
324
286
  }
@@ -47,7 +47,7 @@ export async function orchestrateInterfaceEndpoints<
47
47
  controllers: [
48
48
  createApplication({
49
49
  model: ctx.model,
50
- build: async (endpoints) => {
50
+ build: (endpoints) => {
51
51
  pointer.value = endpoints;
52
52
  },
53
53
  }),
@@ -79,7 +79,7 @@ export async function orchestrateInterfaceEndpoints<
79
79
 
80
80
  function createApplication<Model extends ILlmSchema.Model>(props: {
81
81
  model: Model;
82
- build: (endpoints: AutoBeOpenApi.IEndpoint[]) => Promise<void>;
82
+ build: (endpoints: AutoBeOpenApi.IEndpoint[]) => void;
83
83
  }): IAgenticaController.IClass<Model> {
84
84
  assertSchemaModel(props.model);
85
85
 
@@ -91,11 +91,8 @@ function createApplication<Model extends ILlmSchema.Model>(props: {
91
91
  name: "interface",
92
92
  application,
93
93
  execute: {
94
- makeEndpoints: async (next) => {
95
- await props.build(next.endpoints);
96
- return {
97
- success: true,
98
- };
94
+ makeEndpoints: (next) => {
95
+ props.build(next.endpoints);
99
96
  },
100
97
  } satisfies IApplication,
101
98
  };
@@ -104,7 +104,7 @@ async function process<Model extends ILlmSchema.Model>(
104
104
  controllers: [
105
105
  createApplication({
106
106
  model: ctx.model,
107
- build: async (endpoints) => {
107
+ build: (endpoints) => {
108
108
  pointer.value = endpoints;
109
109
  },
110
110
  pointer,
@@ -129,7 +129,7 @@ async function process<Model extends ILlmSchema.Model>(
129
129
 
130
130
  function createApplication<Model extends ILlmSchema.Model>(props: {
131
131
  model: Model;
132
- build: (operations: AutoBeOpenApi.IOperation[]) => Promise<void>;
132
+ build: (operations: AutoBeOpenApi.IOperation[]) => void;
133
133
  pointer: IPointer<AutoBeOpenApi.IOperation[] | null>;
134
134
  }): IAgenticaController.IClass<Model> {
135
135
  assertSchemaModel(props.model);
@@ -166,11 +166,8 @@ function createApplication<Model extends ILlmSchema.Model>(props: {
166
166
  name: "interface",
167
167
  application,
168
168
  execute: {
169
- makeOperations: async (next) => {
170
- await props.build(next.operations);
171
- return {
172
- success: true,
173
- };
169
+ makeOperations: (next) => {
170
+ props.build(next.operations);
174
171
  },
175
172
  } satisfies IApplication,
176
173
  };
@@ -83,6 +83,8 @@ export const transformInterfaceHistories = (
83
83
  {
84
84
  type: "assistantMessage",
85
85
  text: [
86
+ "Database schema and entity relationship diagrams are ready.",
87
+ "",
86
88
  "## Prisma DB Schema",
87
89
  "```json",
88
90
  JSON.stringify(state.prisma.result.schemas),
@@ -14,7 +14,6 @@ export function orchestratePrismaCompiler<Model extends ILlmSchema.Model>(
14
14
  files: Record<string, string>,
15
15
  retry: number = 8,
16
16
  ): Promise<IAutoBePrismaCompilerResult> {
17
- files["main.prisma"] = MAIN_PRISMA_FILE;
18
17
  return step(ctx, files, retry);
19
18
  }
20
19
 
@@ -23,6 +22,9 @@ async function step<Model extends ILlmSchema.Model>(
23
22
  files: Record<string, string>,
24
23
  life: number,
25
24
  ): Promise<IAutoBePrismaCompilerResult> {
25
+ // FIX MAIN PRISMA FILE
26
+ files["main.prisma"] = MAIN_PRISMA_FILE;
27
+
26
28
  // TRY COMPILATION
27
29
  const result: IAutoBePrismaCompilerResult = await ctx.compiler.prisma({
28
30
  files,