UNPKG

@autobe/agent

Version:

AI backend server code generator

373 lines 27.1 kB
"use strict"; var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) { if (k2 === undefined) k2 = k; var desc = Object.getOwnPropertyDescriptor(m, k); if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) { desc = { enumerable: true, get: function() { return m[k]; } }; } Object.defineProperty(o, k2, desc); }) : (function(o, m, k, k2) { if (k2 === undefined) k2 = k; o[k2] = m[k]; })); var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) { Object.defineProperty(o, "default", { enumerable: true, value: v }); }) : function(o, v) { o["default"] = v; }); var __importStar = (this && this.__importStar) || (function () { var ownKeys = function(o) { ownKeys = Object.getOwnPropertyNames || function (o) { var ar = []; for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k; return ar; }; return ownKeys(o); }; return function (mod) { if (mod && mod.__esModule) return mod; var result = {}; if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]); __setModuleDefault(result, mod); return result; }; })(); var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.orchestrateInterfaceComplement = orchestrateInterfaceComplement; const __typia_transform__accessExpressionAsString = __importStar(require("typia/lib/internal/_accessExpressionAsString.js")); const __typia_transform__validateReport = __importStar(require("typia/lib/internal/_validateReport.js")); const core_1 = require("@agentica/core"); const openapi_1 = require("@samchon/openapi"); const OpenApiV3_1Emender_1 = require("@samchon/openapi/lib/converters/OpenApiV3_1Emender"); const typia_1 = __importDefault(require("typia")); const assertSchemaModel_1 = require("../../context/assertSchemaModel"); const enforceToolCall_1 = require("../../utils/enforceToolCall"); const forceRetry_1 = require("../../utils/forceRetry"); const transformInterfaceComplementHistories_1 = require("./histories/transformInterfaceComplementHistories"); function orchestrateInterfaceComplement(ctx, document, life = 8) { return (0, forceRetry_1.forceRetry)(() => step(ctx, document, life)); } function step(ctx, document, retry) { return __awaiter(this, void 0, void 0, function* () { var _a, _b, _c; const missed = getMissed(document); if (missed.length === 0 || retry <= 0) { return document.components.schemas; } const pointer = { value: null, }; const agentica = new core_1.MicroAgentica({ model: ctx.model, vendor: ctx.vendor, config: Object.assign(Object.assign({}, ((_a = ctx.config) !== null && _a !== void 0 ? _a : {})), { executor: { describe: null, } }), histories: (0, transformInterfaceComplementHistories_1.transformInterfaceComplementHistories)(ctx.state(), document, missed), controllers: [ createApplication({ model: ctx.model, build: (next) => { var _a, _b; (_a = pointer.value) !== null && _a !== void 0 ? _a : (pointer.value = {}); Object.assign(pointer.value, ((_b = OpenApiV3_1Emender_1.OpenApiV3_1Emender.convertComponents({ schemas: next, }).schemas) !== null && _b !== void 0 ? _b : {})); }, }), ], }); (0, enforceToolCall_1.enforceToolCall)(agentica); yield agentica.conversate("Fill missing schema types please").finally(() => { const tokenUsage = agentica.getTokenUsage(); ctx.usage().record(tokenUsage, ["interface"]); }); if (pointer.value === null) { // unreachable throw new Error("Failed to fill missing schema types. No response from agentica."); } ctx.dispatch({ type: "interfaceComplement", missed, schemas: pointer.value, step: (_c = (_b = ctx.state().analyze) === null || _b === void 0 ? void 0 : _b.step) !== null && _c !== void 0 ? _c : 0, created_at: new Date().toISOString(), }); const newSchemas = Object.assign(Object.assign({}, pointer.value), document.components.schemas); return step(ctx, Object.assign(Object.assign({}, document), { components: Object.assign(Object.assign({}, document.components), { schemas: newSchemas }) }), retry - 1); }); } const getMissed = (document) => { const missed = new Set(); const check = (name) => { if (document.components.schemas[name] === undefined) missed.add(name); }; for (const op of document.operations) { if (op.requestBody !== null) check(op.requestBody.typeName); if (op.responseBody !== null) check(op.responseBody.typeName); } for (const value of Object.values(document.components.schemas)) openapi_1.OpenApiTypeChecker.visit({ components: document.components, schema: value, closure: (next) => { if (openapi_1.OpenApiTypeChecker.isReference(next)) check(next.$ref.split("/").pop()); }, }); return Array.from(missed); }; function createApplication(props) { (0, assertSchemaModel_1.assertSchemaModel)(props.model); const application = collection[props.model]; return { protocol: "class", name: "interface", application, execute: { complementComponents: (next) => { props.build(next.schemas); }, }, }; } const claude = { model: "claude", options: { reference: true, separate: null }, functions: [ { name: "complementComponents", parameters: { description: "Current Type: {@link IAutoBeInterfaceComplementApplication.IProps}", type: "object", properties: { schemas: { description: "A collection of missing schema definitions that need to be added to the\nOpenAPI document's `components.schemas` section.\n\nThis object contains schema definitions for types that are referenced but\nnot yet defined:\n\n- Key: Schema name (`string`): The name of the schema type that will be\n referenced in $ref statements\n- Value: `AutoBeOpenApi.IJsonSchema` - The complete JSON Schema definition\n for that type\n\nExample structure:\n\n```typescript\n{\n \"UserProfile\": {\n \"type\": \"object\",\n \"properties\": {\n \"id\": { \"type\": \"string\" },\n \"name\": { \"type\": \"string\" },\n \"email\": { \"type\": \"string\", \"format\": \"email\" }\n },\n \"required\": [\"id\", \"name\", \"email\"]\n }\n}\n```\n\nEach schema definition follows the JSON Schema specification and will be\ndirectly inserted into the OpenAPI document's components.schemas section,\nmaking them available for $ref references throughout the API\nspecification.", $ref: "#/$defs/RecordstringAutoBeOpenApi.IJsonSchemaDescriptiveAutoBeOpenApi.IJsonSchema" } }, required: [ "schemas" ], additionalProperties: false, $defs: { "RecordstringAutoBeOpenApi.IJsonSchemaDescriptiveAutoBeOpenApi.IJsonSchema": { description: "Construct a type with a set of properties K of type T", type: "object", properties: {}, required: [], additionalProperties: { $ref: "#/$defs/AutoBeOpenApi.IJsonSchemaDescriptiveAutoBeOpenApi.IJsonSchema" } }, "AutoBeOpenApi.IJsonSchemaDescriptiveAutoBeOpenApi.IJsonSchema": { description: "Descriptive type schema info.\n\n`AutoBeOpenApi.IJsonSchemaDescriptive` is a type schema info of the OpenAPI\nGenerative, but it has a `description` property which is required.\n\n`AutoBeOpenApi.IJsonSchemaDescriptive` basically follows the JSON schema\nspecification of OpenAPI v3.1, but a little bit shrunk to remove ambiguous\nand duplicated expressions of OpenAPI v3.1 for the convenience, clarity,\nand AI generation.\n\nCRITICAL INSTRUCTIONS FOR OPTIMAL AI GENERATION:\n\nWhen creating descriptions for components, types, and properties:\n\n1. ALWAYS refer to and incorporate the description comments from the\n corresponding Prisma DB schema tables and columns. The descriptions\n should match the style, level of detail, and terminology used in the\n Prisma schema.\n2. ALL descriptions MUST be organized into MULTIPLE PARAGRAPHS separated by\n line breaks. Single-paragraph descriptions should be avoided.\n3. Descriptions should comprehensively cover:\n\n - The purpose and business meaning of the type or property\n - Relationships to other entities\n - Validation rules, constraints, and edge cases\n - Usage context and examples when helpful\n4. For each property of an object type, ensure its description reflects the\n corresponding column description in the Prisma DB schema, maintaining\n the same level of detail and terminology\n5. Descriptions should be so detailed and clear that anyone reading them can\n fully understand the type or property without needing to reference any\n other documentation", type: "object", properties: { description: { description: "Description about the type.\n\nCRITICAL: This description MUST be extensively detailed and MUST\nreference and align with the description comments from the\ncorresponding Prisma DB schema tables and columns.\n\nThe description MUST be organized into MULTIPLE PARAGRAPHS (separated\nby line breaks) based on different aspects of the type:\n\n- The purpose and business meaning of the type\n- Relationships to other entities in the system\n- Validation rules, constraints, and edge cases\n- Usage context and examples when helpful\n\nThis structured approach improves readability and helps readers better\nunderstand the type's various characteristics and use cases. The\ndescription should be so comprehensive that anyone reading it can fully\nunderstand the type without needing to reference other documentation.\n\n> MUST be written in English. Never use other languages.", type: "string" } }, required: [ "description" ] } } }, description: "Complements missing schema types\n\nThis method fills in schema definitions that are referenced via $ref but\nnot yet defined in the `components.schemas` section. For example, if an API\noperation references `{ \"$ref\": \"#/components/schemas/UserProfile\" }` but\n`UserProfile` type is not defined in `components.schemas`, this method will\nadd the missing schema definition.\n\nThis function is designed to be called via AI function calling mechanism to\nensure the OpenAPI document is complete and all referenced schemas are\nproperly defined.", validate: (() => { const _io0 = input => "object" === typeof input.schemas && null !== input.schemas && false === Array.isArray(input.schemas) && _io1(input.schemas); const _io1 = input => Object.keys(input).every(key => { const value = input[key]; if (undefined === value) return true; return "object" === typeof value && null !== value && _io2(value); }); const _io2 = input => "string" === typeof input.description; const _vo0 = (input, _path, _exceptionable = true) => [("object" === typeof input.schemas && null !== input.schemas && false === Array.isArray(input.schemas) || _report(_exceptionable, { path: _path + ".schemas", expected: "Record<string, AutoBeOpenApi.IJsonSchemaDescriptive<AutoBeOpenApi.IJsonSchema>>", value: input.schemas })) && _vo1(input.schemas, _path + ".schemas", true && _exceptionable) || _report(_exceptionable, { path: _path + ".schemas", expected: "Record<string, AutoBeOpenApi.IJsonSchemaDescriptive<AutoBeOpenApi.IJsonSchema>>", value: input.schemas })].every(flag => flag); const _vo1 = (input, _path, _exceptionable = true) => [false === _exceptionable || Object.keys(input).map(key => { const value = input[key]; if (undefined === value) return true; return ("object" === typeof value && null !== value || _report(_exceptionable, { path: _path + __typia_transform__accessExpressionAsString._accessExpressionAsString(key), expected: "AutoBeOpenApi.IJsonSchemaDescriptive<AutoBeOpenApi.IJsonSchema>", value: value })) && _vo2(value, _path + __typia_transform__accessExpressionAsString._accessExpressionAsString(key), true && _exceptionable) || _report(_exceptionable, { path: _path + __typia_transform__accessExpressionAsString._accessExpressionAsString(key), expected: "AutoBeOpenApi.IJsonSchemaDescriptive<AutoBeOpenApi.IJsonSchema>", value: value }); }).every(flag => flag)].every(flag => flag); const _vo2 = (input, _path, _exceptionable = true) => ["string" === typeof input.description || _report(_exceptionable, { path: _path + ".description", expected: "string", value: input.description })].every(flag => flag); const __is = input => "object" === typeof input && null !== input && _io0(input); let errors; let _report; return input => { if (false === __is(input)) { errors = []; _report = __typia_transform__validateReport._validateReport(errors); ((input, _path, _exceptionable = true) => ("object" === typeof input && null !== input || _report(true, { path: _path + "", expected: "IAutoBeInterfaceComplementApplication.IProps", value: input })) && _vo0(input, _path + "", true) || _report(true, { path: _path + "", expected: "IAutoBeInterfaceComplementApplication.IProps", value: input }))(input, "$input", true); const success = 0 === errors.length; return success ? { success, data: input } : { success, errors, data: input }; } return { success: true, data: input }; }; })() } ] }; const collection = { chatgpt: { model: "chatgpt", options: { reference: true, strict: false, separate: null }, functions: [ { name: "complementComponents", parameters: { description: "Current Type: {@link IAutoBeInterfaceComplementApplication.IProps}\n\n### Description of {@link schemas} property:\n\n> A collection of missing schema definitions that need to be added to the\n> OpenAPI document's `components.schemas` section.\n> \n> This object contains schema definitions for types that are referenced but\n> not yet defined:\n> \n> - Key: Schema name (`string`): The name of the schema type that will be\n> referenced in $ref statements\n> - Value: `AutoBeOpenApi.IJsonSchema` - The complete JSON Schema definition\n> for that type\n> \n> Example structure:\n> \n> ```typescript\n> {\n> \"UserProfile\": {\n> \"type\": \"object\",\n> \"properties\": {\n> \"id\": { \"type\": \"string\" },\n> \"name\": { \"type\": \"string\" },\n> \"email\": { \"type\": \"string\", \"format\": \"email\" }\n> },\n> \"required\": [\"id\", \"name\", \"email\"]\n> }\n> }\n> ```\n> \n> Each schema definition follows the JSON Schema specification and will be\n> directly inserted into the OpenAPI document's components.schemas section,\n> making them available for $ref references throughout the API\n> specification.", type: "object", properties: { schemas: { $ref: "#/$defs/RecordstringAutoBeOpenApi.IJsonSchemaDescriptiveAutoBeOpenApi.IJsonSchema" } }, required: [ "schemas" ], additionalProperties: false, $defs: { "RecordstringAutoBeOpenApi.IJsonSchemaDescriptiveAutoBeOpenApi.IJsonSchema": { description: "Construct a type with a set of properties K of type T", type: "object", properties: {}, required: [], additionalProperties: { $ref: "#/$defs/AutoBeOpenApi.IJsonSchemaDescriptiveAutoBeOpenApi.IJsonSchema" } }, "AutoBeOpenApi.IJsonSchemaDescriptiveAutoBeOpenApi.IJsonSchema": { description: "Descriptive type schema info.\n\n`AutoBeOpenApi.IJsonSchemaDescriptive` is a type schema info of the OpenAPI\nGenerative, but it has a `description` property which is required.\n\n`AutoBeOpenApi.IJsonSchemaDescriptive` basically follows the JSON schema\nspecification of OpenAPI v3.1, but a little bit shrunk to remove ambiguous\nand duplicated expressions of OpenAPI v3.1 for the convenience, clarity,\nand AI generation.\n\nCRITICAL INSTRUCTIONS FOR OPTIMAL AI GENERATION:\n\nWhen creating descriptions for components, types, and properties:\n\n1. ALWAYS refer to and incorporate the description comments from the\n corresponding Prisma DB schema tables and columns. The descriptions\n should match the style, level of detail, and terminology used in the\n Prisma schema.\n2. ALL descriptions MUST be organized into MULTIPLE PARAGRAPHS separated by\n line breaks. Single-paragraph descriptions should be avoided.\n3. Descriptions should comprehensively cover:\n\n - The purpose and business meaning of the type or property\n - Relationships to other entities\n - Validation rules, constraints, and edge cases\n - Usage context and examples when helpful\n4. For each property of an object type, ensure its description reflects the\n corresponding column description in the Prisma DB schema, maintaining\n the same level of detail and terminology\n5. Descriptions should be so detailed and clear that anyone reading them can\n fully understand the type or property without needing to reference any\n other documentation", type: "object", properties: { description: { description: "Description about the type.\n\nCRITICAL: This description MUST be extensively detailed and MUST\nreference and align with the description comments from the\ncorresponding Prisma DB schema tables and columns.\n\nThe description MUST be organized into MULTIPLE PARAGRAPHS (separated\nby line breaks) based on different aspects of the type:\n\n- The purpose and business meaning of the type\n- Relationships to other entities in the system\n- Validation rules, constraints, and edge cases\n- Usage context and examples when helpful\n\nThis structured approach improves readability and helps readers better\nunderstand the type's various characteristics and use cases. The\ndescription should be so comprehensive that anyone reading it can fully\nunderstand the type without needing to reference other documentation.\n\n> MUST be written in English. Never use other languages.", type: "string" } }, required: [ "description" ] } } }, description: "Complements missing schema types\n\nThis method fills in schema definitions that are referenced via $ref but\nnot yet defined in the `components.schemas` section. For example, if an API\noperation references `{ \"$ref\": \"#/components/schemas/UserProfile\" }` but\n`UserProfile` type is not defined in `components.schemas`, this method will\nadd the missing schema definition.\n\nThis function is designed to be called via AI function calling mechanism to\nensure the OpenAPI document is complete and all referenced schemas are\nproperly defined.", validate: (() => { const _io0 = input => "object" === typeof input.schemas && null !== input.schemas && false === Array.isArray(input.schemas) && _io1(input.schemas); const _io1 = input => Object.keys(input).every(key => { const value = input[key]; if (undefined === value) return true; return "object" === typeof value && null !== value && _io2(value); }); const _io2 = input => "string" === typeof input.description; const _vo0 = (input, _path, _exceptionable = true) => [("object" === typeof input.schemas && null !== input.schemas && false === Array.isArray(input.schemas) || _report(_exceptionable, { path: _path + ".schemas", expected: "Record<string, AutoBeOpenApi.IJsonSchemaDescriptive<AutoBeOpenApi.IJsonSchema>>", value: input.schemas })) && _vo1(input.schemas, _path + ".schemas", true && _exceptionable) || _report(_exceptionable, { path: _path + ".schemas", expected: "Record<string, AutoBeOpenApi.IJsonSchemaDescriptive<AutoBeOpenApi.IJsonSchema>>", value: input.schemas })].every(flag => flag); const _vo1 = (input, _path, _exceptionable = true) => [false === _exceptionable || Object.keys(input).map(key => { const value = input[key]; if (undefined === value) return true; return ("object" === typeof value && null !== value || _report(_exceptionable, { path: _path + __typia_transform__accessExpressionAsString._accessExpressionAsString(key), expected: "AutoBeOpenApi.IJsonSchemaDescriptive<AutoBeOpenApi.IJsonSchema>", value: value })) && _vo2(value, _path + __typia_transform__accessExpressionAsString._accessExpressionAsString(key), true && _exceptionable) || _report(_exceptionable, { path: _path + __typia_transform__accessExpressionAsString._accessExpressionAsString(key), expected: "AutoBeOpenApi.IJsonSchemaDescriptive<AutoBeOpenApi.IJsonSchema>", value: value }); }).every(flag => flag)].every(flag => flag); const _vo2 = (input, _path, _exceptionable = true) => ["string" === typeof input.description || _report(_exceptionable, { path: _path + ".description", expected: "string", value: input.description })].every(flag => flag); const __is = input => "object" === typeof input && null !== input && _io0(input); let errors; let _report; return input => { if (false === __is(input)) { errors = []; _report = __typia_transform__validateReport._validateReport(errors); ((input, _path, _exceptionable = true) => ("object" === typeof input && null !== input || _report(true, { path: _path + "", expected: "IAutoBeInterfaceComplementApplication.IProps", value: input })) && _vo0(input, _path + "", true) || _report(true, { path: _path + "", expected: "IAutoBeInterfaceComplementApplication.IProps", value: input }))(input, "$input", true); const success = 0 === errors.length; return success ? { success, data: input } : { success, errors, data: input }; } return { success: true, data: input }; }; })() } ] }, claude, llama: claude, deepseek: claude, "3.1": claude, }; //# sourceMappingURL=orchestrateInterfaceComplement.js.map