api-core-lib 12.12.102 → 12.12.104

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 (2) hide show
  1. package/dist/cli.cjs +323 -72
  2. package/package.json +1 -1
package/dist/cli.cjs CHANGED
@@ -74,7 +74,7 @@ var import_chalk = __toESM(require("chalk"), 1);
74
74
  var import_dotenv = __toESM(require("dotenv"), 1);
75
75
  var import_swagger_parser = __toESM(require("@apidevtools/swagger-parser"), 1);
76
76
  var import_openapi_types = __toESM(require_dist(), 1);
77
- var inquirer = __toESM(require("inquirer"), 1);
77
+ var import_inquirer = __toESM(require("inquirer"), 1);
78
78
  var DEBUG_MODE = process.env.DEBUG === "true";
79
79
  var debugLog = (title, data) => DEBUG_MODE && console.log(import_chalk.default.yellow(`
80
80
  [DEBUG: ${title}]`), import_util.default.inspect(data, { depth: 5, colors: true }));
@@ -88,19 +88,93 @@ function findCommonPath(paths) {
88
88
  const first = sortedPaths[0].split("/");
89
89
  const last = sortedPaths[sortedPaths.length - 1].split("/");
90
90
  let i = 0;
91
- while (i < first.length && first[i] === last[i]) {
92
- i++;
93
- }
91
+ while (i < first.length && first[i] === last[i]) i++;
94
92
  return first.slice(0, i).join("/") || "/";
95
93
  }
94
+ function _propToZod(prop) {
95
+ let zodChain;
96
+ const getMsg = (key) => `{ "message": "validation.${key}" }`;
97
+ switch (prop.type) {
98
+ case "string":
99
+ if (prop.enumName) {
100
+ zodChain = `z.enum(${prop.enumName})`;
101
+ } else {
102
+ zodChain = "z.string()";
103
+ if (prop.isRequired) zodChain += `.min(1, ${getMsg("string.nonempty")})`;
104
+ if (prop.maxLength !== void 0) zodChain += `.max(${prop.maxLength}, ${getMsg("string.max")})`;
105
+ if (prop.pattern) zodChain += `.regex(/${prop.pattern}/, ${getMsg("string.regex")})`;
106
+ if (prop.format === "email") zodChain += `.email(${getMsg("string.email")})`;
107
+ if (prop.format === "url") zodChain += `.url(${getMsg("string.url")})`;
108
+ if (prop.format === "uuid") zodChain += `.uuid(${getMsg("string.uuid")})`;
109
+ }
110
+ break;
111
+ case "integer":
112
+ case "number":
113
+ zodChain = prop.type === "integer" ? `z.number().int(${getMsg("number.integer")})` : "z.number()";
114
+ if (prop.minimum !== void 0) zodChain += `.min(${prop.minimum}, ${getMsg("number.min")})`;
115
+ if (prop.maximum !== void 0) zodChain += `.max(${prop.maximum}, ${getMsg("number.max")})`;
116
+ break;
117
+ case "boolean":
118
+ zodChain = `z.boolean()`;
119
+ break;
120
+ case "array":
121
+ const itemSchema = prop.items ? _propToZod(prop.items) : "z.any()";
122
+ zodChain = `z.array(${itemSchema})`;
123
+ if (prop.minItems !== void 0) zodChain += `.min(${prop.minItems}, ${getMsg("array.min")})`;
124
+ if (prop.maxItems !== void 0) zodChain += `.max(${prop.maxItems}, ${getMsg("array.max")})`;
125
+ break;
126
+ case "object":
127
+ if (prop.properties && prop.properties.length > 0) {
128
+ const shape = prop.properties.map((p) => ` ${p.name}: ${_propToZod(p)}`).join(",\n");
129
+ zodChain = `z.object({
130
+ ${shape}
131
+ })`;
132
+ } else {
133
+ zodChain = "z.record(z.unknown())";
134
+ }
135
+ break;
136
+ default:
137
+ zodChain = "z.any()";
138
+ break;
139
+ }
140
+ if (prop.description) zodChain += `.describe(${JSON.stringify(prop.description)})`;
141
+ if (!prop.isRequired) zodChain += ".optional()";
142
+ if (prop.isNullable) zodChain += ".nullable()";
143
+ return zodChain;
144
+ }
145
+ function _propToMock(prop) {
146
+ if (prop.example) return prop.example;
147
+ if (prop.name.match(/image|avatar|logo|url/i)) return "https://via.placeholder.com/150";
148
+ if (prop.enum) return prop.enum[0];
149
+ switch (prop.type) {
150
+ case "string":
151
+ if (prop.format === "email") return "test@example.com";
152
+ if (prop.format === "uuid") return "a0eebc99-9c0b-4ef8-bb6d-6bb9bd380a11";
153
+ return `Mock ${toPascalCase(prop.name)}`;
154
+ case "integer":
155
+ case "number":
156
+ return 1;
157
+ case "boolean":
158
+ return true;
159
+ case "array":
160
+ return prop.items ? [_propToMock(prop.items)] : [];
161
+ case "object":
162
+ const mock = {};
163
+ if (prop.properties) prop.properties.forEach((p) => {
164
+ mock[p.name] = _propToMock(p);
165
+ });
166
+ return mock;
167
+ default:
168
+ return null;
169
+ }
170
+ }
96
171
  function parseSchema(name, schema, allEnums) {
97
172
  const properties = [];
98
173
  const enums = {};
99
174
  if (schema.properties) {
100
175
  for (const propName in schema.properties) {
101
176
  const propSchema = schema.properties[propName];
102
- let itemSchema;
103
- let generatedEnumName;
177
+ let itemSchema, generatedEnumName;
104
178
  if (propSchema.type === "array" && propSchema.items) {
105
179
  const itemTypeName = `${toPascalCase(name)}${toPascalCase(propName)}Item`;
106
180
  itemSchema = parseSchema(itemTypeName, propSchema.items, allEnums).properties[0];
@@ -113,55 +187,25 @@ function parseSchema(name, schema, allEnums) {
113
187
  }
114
188
  generatedEnumName = enumName;
115
189
  }
116
- properties.push({
117
- name: propName,
118
- type: propSchema.type || "object",
119
- isRequired: (schema.required || []).includes(propName),
120
- isNullable: propSchema.nullable || false,
121
- description: propSchema.description,
122
- example: propSchema.example,
123
- enum: propSchema.enum,
124
- enumName: generatedEnumName,
125
- format: propSchema.format,
126
- items: itemSchema,
127
- properties: propSchema.properties ? parseSchema(`${name}${toPascalCase(propName)}`, propSchema, allEnums).properties : void 0,
128
- minLength: propSchema.minLength,
129
- maxLength: propSchema.maxLength,
130
- pattern: propSchema.pattern,
131
- minimum: propSchema.minimum,
132
- maximum: propSchema.maximum,
133
- minItems: propSchema.minItems,
134
- maxItems: propSchema.maxItems
135
- });
190
+ properties.push({ name: propName, type: propSchema.type || "object", isRequired: (schema.required || []).includes(propName), isNullable: propSchema.nullable || false, description: propSchema.description, example: propSchema.example, enum: propSchema.enum, enumName: generatedEnumName, format: propSchema.format, items: itemSchema, properties: propSchema.properties ? parseSchema(`${name}${toPascalCase(propName)}`, propSchema, allEnums).properties : void 0, minLength: propSchema.minLength, maxLength: propSchema.maxLength, pattern: propSchema.pattern, minimum: propSchema.minimum, maximum: propSchema.maximum, minItems: propSchema.minItems, maxItems: propSchema.maxItems });
136
191
  }
137
192
  }
138
193
  return { name, description: schema.description, properties, enums };
139
194
  }
140
195
  function parseSpecToModules(spec) {
141
- const modules = /* @__PURE__ */ new Map();
142
- const allSchemas = /* @__PURE__ */ new Map();
143
- const allEnums = /* @__PURE__ */ new Map();
144
- const modulePaths = /* @__PURE__ */ new Map();
196
+ const modules = /* @__PURE__ */ new Map(), allSchemas = /* @__PURE__ */ new Map(), allEnums = /* @__PURE__ */ new Map(), modulePaths = /* @__PURE__ */ new Map();
145
197
  const BUILT_IN_TYPES = /* @__PURE__ */ new Set(["string", "number", "boolean", "void", "undefined", "unknown", "any", "Date", "Promise", "QueryOptions", "Record<string, any>", "Record<string, unknown>"]);
146
198
  const registerSchema = (schema, baseName) => {
147
199
  if (!schema) return "Record<string, any>";
148
200
  if (schema.type === "array" && schema.items) {
149
- const itemSchema = schema.items;
150
- const itemBaseName = `${baseName}Item`;
151
- if (itemSchema.properties || itemSchema.type === "object") {
152
- return `${registerSchema(itemSchema, itemBaseName)}[]`;
153
- }
154
- const primitiveType = itemSchema.type === "integer" ? "number" : itemSchema.type || "any";
155
- return `${primitiveType}[]`;
201
+ const itemSchema = schema.items, itemBaseName = `${baseName}Item`;
202
+ if (itemSchema.properties || itemSchema.type === "object") return `${registerSchema(itemSchema, itemBaseName)}[]`;
203
+ return `${itemSchema.type === "integer" ? "number" : itemSchema.type || "any"}[]`;
156
204
  }
157
205
  if (schema.type === "object" || schema.properties || schema.allOf || !schema.type) {
158
- if (!schema.properties && !schema.allOf) {
159
- return "Record<string, any>";
160
- }
206
+ if (!schema.properties && !schema.allOf) return "Record<string, any>";
161
207
  const typeName = toPascalCase(baseName.replace(/_v\d+(Request|Response)$/, "$1"));
162
- if (!allSchemas.has(typeName)) {
163
- allSchemas.set(typeName, parseSchema(typeName, schema, allEnums));
164
- }
208
+ if (!allSchemas.has(typeName)) allSchemas.set(typeName, parseSchema(typeName, schema, allEnums));
165
209
  return typeName;
166
210
  }
167
211
  return schema.type === "integer" ? "number" : schema.type || "any";
@@ -173,8 +217,7 @@ function parseSpecToModules(spec) {
173
217
  if (!Object.values(import_openapi_types.OpenAPIV3.HttpMethods).includes(method)) continue;
174
218
  const endpoint = pathItem[method];
175
219
  if (!endpoint.tags || endpoint.tags.length === 0 || !endpoint.operationId) continue;
176
- const tagName = endpoint.tags[0];
177
- const moduleName = sanitizeForModuleName(tagName);
220
+ const moduleName = sanitizeForModuleName(endpoint.tags[0]);
178
221
  if (!modules.has(moduleName)) {
179
222
  modules.set(moduleName, { moduleName, baseEndpoint: "", actions: {}, schemas: /* @__PURE__ */ new Set(), enums: /* @__PURE__ */ new Set() });
180
223
  modulePaths.set(moduleName, []);
@@ -186,11 +229,8 @@ function parseSpecToModules(spec) {
186
229
  const outputType = successKey === "204" ? "void" : registerSchema(successRes?.content?.["application/json"]?.schema, `${endpoint.operationId}Response`);
187
230
  const reqBody = endpoint.requestBody;
188
231
  let inputType = "undefined";
189
- if (reqBody?.content?.["application/json"]?.schema) {
190
- inputType = registerSchema(reqBody.content["application/json"].schema, `${endpoint.operationId}Request`);
191
- } else if ((endpoint.parameters || []).some((p) => p.in === "query")) {
192
- inputType = "QueryOptions";
193
- }
232
+ if (reqBody?.content?.["application/json"]?.schema) inputType = registerSchema(reqBody.content["application/json"].schema, `${endpoint.operationId}Request`);
233
+ else if ((endpoint.parameters || []).some((p) => p.in === "query")) inputType = "QueryOptions";
194
234
  [inputType, outputType].forEach((t) => {
195
235
  const cleanType = t.replace("[]", "");
196
236
  if (cleanType && !BUILT_IN_TYPES.has(cleanType)) {
@@ -199,20 +239,7 @@ function parseSpecToModules(spec) {
199
239
  if (schemaDef) Object.keys(schemaDef.enums).forEach((propName) => currentModule.enums.add(`${toPascalCase(cleanType)}${toPascalCase(propName)}Enum`));
200
240
  }
201
241
  });
202
- const actionName = getActionName(endpoint.operationId);
203
- const pathParams = (apiPath.match(/{(\w+)}/g) || []).map((p) => p.slice(1, -1));
204
- currentModule.actions[actionName] = {
205
- name: actionName,
206
- method: method.toUpperCase(),
207
- path: apiPath,
208
- description: endpoint.summary || "",
209
- hasQuery: (endpoint.parameters || []).some((p) => p.in === "query"),
210
- autoFetch: method.toUpperCase() === "GET" && !apiPath.includes("{"),
211
- requiresAuth: !!endpoint.security && endpoint.security.length > 0,
212
- inputType,
213
- outputType,
214
- pathParams
215
- };
242
+ currentModule.actions[getActionName(endpoint.operationId)] = { name: getActionName(endpoint.operationId), method: method.toUpperCase(), path: apiPath, description: endpoint.summary || "", hasQuery: (endpoint.parameters || []).some((p) => p.in === "query"), autoFetch: method.toUpperCase() === "GET" && !apiPath.includes("{"), requiresAuth: !!endpoint.security && endpoint.security.length > 0, inputType, outputType, pathParams: (apiPath.match(/{(\w+)}/g) || []).map((p) => p.slice(1, -1)) };
216
243
  }
217
244
  }
218
245
  modules.forEach((mod, name) => {
@@ -227,12 +254,236 @@ async function generateModuleFiles(module2, allSchemas, allEnums, outputDir) {
227
254
  if (!import_fs.default.existsSync(moduleOutputPath)) import_fs.default.mkdirSync(moduleOutputPath, { recursive: true });
228
255
  console.log(import_chalk.default.cyan(`
229
256
  Generating module: ${import_chalk.default.bold(module2.moduleName)}`));
230
- console.log(import_chalk.default.gray(` \u2713 (Simulated) Generated files for ${module2.moduleName}.`));
257
+ const BUILT_IN_TYPES = /* @__PURE__ */ new Set(["string", "number", "boolean", "void", "undefined", "unknown", "any", "Date", "Promise", "QueryOptions", "Record<string, any>", "Record<string, unknown>"]);
258
+ const schemasToImport = [...module2.schemas].filter((name) => !BUILT_IN_TYPES.has(name)).sort();
259
+ const enumsToImport = [...module2.enums].sort();
260
+ const createdFileExports = ["config"];
261
+ let configContent = `// Auto-generated file. Do not edit.
262
+
263
+ import type { ApiModuleConfig, ActionConfigModule, QueryOptions } from 'api-core-lib';
264
+ `;
265
+ if (schemasToImport.length > 0) configContent += `import type { ${schemasToImport.join(", ")} } from './types';
266
+ `;
267
+ const actionsType = Object.values(module2.actions).map((a) => ` ${a.name}: ActionConfigModule<${a.inputType}, ${a.outputType}>;`).join("\n");
268
+ const actionsValue = Object.values(module2.actions).map((a) => {
269
+ const { inputType, outputType, name, ...c } = a;
270
+ return ` ${name}: ${JSON.stringify(c, null, 2).replace(/\n/g, "\n ")}`;
271
+ }).join(",\n");
272
+ configContent += `
273
+ export const ${module2.moduleName}: ApiModuleConfig<{
274
+ ${actionsType}
275
+ }> = {
276
+ baseEndpoint: '${module2.baseEndpoint}',
277
+ actions: {
278
+ ${actionsValue}
279
+ },
280
+ };
281
+ `;
282
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, "config.ts"), configContent.trim());
283
+ console.log(import_chalk.default.gray(` \u2713 config.ts`));
284
+ if (schemasToImport.length > 0) {
285
+ if (enumsToImport.length > 0) {
286
+ let enumsContent = `// Auto-generated file. Do not edit.
287
+
288
+ `;
289
+ enumsToImport.forEach((enumName) => {
290
+ const enumDef = allEnums.get(enumName);
291
+ if (enumDef) {
292
+ enumsContent += `export const ${enumName} = ${JSON.stringify(enumDef.values)} as const;
293
+ `;
294
+ enumsContent += `export type ${enumName} = typeof ${enumName}[number];
295
+
296
+ `;
297
+ }
298
+ });
299
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, "enums.ts"), enumsContent.trim());
300
+ console.log(import_chalk.default.gray(` \u2713 enums.ts`));
301
+ createdFileExports.push("enums");
302
+ }
303
+ let typesContent = `// Auto-generated file. Do not edit.
304
+
305
+ `;
306
+ if (enumsToImport.length > 0) typesContent += `import type { ${enumsToImport.join(", ")} } from './enums';
307
+
308
+ `;
309
+ schemasToImport.forEach((typeName) => {
310
+ const parsedSchema = allSchemas.get(typeName);
311
+ if (parsedSchema) {
312
+ if (parsedSchema.description) typesContent += `/** ${parsedSchema.description} */
313
+ `;
314
+ typesContent += `export interface ${typeName} {
315
+ `;
316
+ parsedSchema.properties.forEach((prop) => {
317
+ if (prop.description) typesContent += ` /** ${prop.description} */
318
+ `;
319
+ let propType = prop.enumName || (prop.items ? `${prop.items.type || "any"}[]` : prop.type);
320
+ if (propType === "integer") propType = "number";
321
+ if (propType === "object") propType = "Record<string, any>";
322
+ typesContent += ` ${prop.name}${prop.isRequired ? "" : "?"}: ${propType};
323
+ `;
324
+ });
325
+ typesContent += `}
326
+
327
+ `;
328
+ }
329
+ });
330
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, "types.ts"), typesContent.trim());
331
+ console.log(import_chalk.default.gray(` \u2713 types.ts`));
332
+ createdFileExports.push("types");
333
+ let validationContent = `// Auto-generated file. Do not edit.
334
+
335
+ import { z } from 'zod';
336
+ `;
337
+ if (enumsToImport.length > 0) validationContent += `import { ${enumsToImport.join(", ")} } from './enums';
338
+ `;
339
+ schemasToImport.forEach((typeName) => {
340
+ const parsedSchema = allSchemas.get(typeName);
341
+ if (parsedSchema) {
342
+ const zodShape = parsedSchema.properties.map((p) => ` ${p.name}: ${_propToZod(p)}`).join(",\n");
343
+ validationContent += `
344
+ /** Zod schema for {@link ${typeName}}. */
345
+ `;
346
+ validationContent += `export const ${typeName}Schema = z.object({
347
+ ${zodShape}
348
+ });
349
+
350
+ `;
351
+ validationContent += `export type ${typeName}Validated = z.infer<typeof ${typeName}Schema>;
352
+ `;
353
+ }
354
+ });
355
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, "validation.ts"), validationContent.trim());
356
+ console.log(import_chalk.default.gray(` \u2713 validation.ts`));
357
+ createdFileExports.push("validation");
358
+ let mocksContent = `// Auto-generated file. Do not edit.
359
+ import type { ${schemasToImport.join(", ")} } from './types';
360
+ `;
361
+ if (enumsToImport.length > 0) mocksContent += `import { ${enumsToImport.join(", ")} } from './enums';
362
+
363
+ `;
364
+ schemasToImport.forEach((typeName) => {
365
+ const parsedSchema = allSchemas.get(typeName);
366
+ if (parsedSchema) {
367
+ const mockObject = {};
368
+ parsedSchema.properties.forEach((p) => {
369
+ mockObject[p.name] = _propToMock(p);
370
+ });
371
+ mocksContent += `export const mock${typeName}: ${typeName} = ${JSON.stringify(mockObject, null, 2)};
372
+
373
+ `;
374
+ }
375
+ });
376
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, "mocks.ts"), mocksContent.trim());
377
+ console.log(import_chalk.default.gray(` \u2713 mocks.ts`));
378
+ createdFileExports.push("mocks");
379
+ }
380
+ const indexFilePath = import_path.default.join(moduleOutputPath, "index.ts");
381
+ const initialIndexContent = `// Auto-generated file. Do not edit.
382
+ ` + createdFileExports.map((e) => `export * from './${e}';`).join("\n");
383
+ import_fs.default.writeFileSync(indexFilePath, initialIndexContent);
384
+ console.log(import_chalk.default.gray(` \u2713 index.ts (Initial Entry Point)`));
385
+ const moduleBaseName = module2.moduleName.replace(/Api$/, "");
386
+ const camelCaseModuleName = toCamelCase(moduleBaseName);
387
+ let endpointsContent = `// Auto-generated file. Do not edit.
388
+
389
+ `;
390
+ endpointsContent += `import type { QueryOptions } from 'api-core-lib';
391
+ `;
392
+ const endpointTypesToImport = /* @__PURE__ */ new Set();
393
+ Object.values(module2.actions).forEach((action) => {
394
+ if (action.inputType !== "undefined" && action.inputType !== "QueryOptions" && !BUILT_IN_TYPES.has(action.inputType)) {
395
+ endpointTypesToImport.add(action.inputType);
396
+ }
397
+ });
398
+ if (endpointTypesToImport.size > 0) {
399
+ endpointsContent += `import type { ${[...endpointTypesToImport].join(", ")} } from './types';
400
+
401
+ `;
402
+ }
403
+ endpointsContent += `export const ${camelCaseModuleName}Endpoints = {
404
+ `;
405
+ for (const action of Object.values(module2.actions)) {
406
+ const params = [];
407
+ if (action.pathParams.length > 0) params.push(`params: { ${action.pathParams.map((p) => `${p}: string | number`).join("; ")} }`);
408
+ if (action.inputType !== "undefined" && action.inputType !== "QueryOptions") params.push(`body: ${action.inputType}`);
409
+ if (action.hasQuery) params.push(`query?: QueryOptions`);
410
+ endpointsContent += ` /**
411
+ * ${action.method} ${module2.baseEndpoint}${action.path}
412
+ * ${action.description}
413
+ */
414
+ `;
415
+ endpointsContent += ` ${action.name}: (${params.join(", ")}) => ({
416
+ `;
417
+ endpointsContent += ` action: '${action.name}' as const,
418
+ `;
419
+ if (action.pathParams.length > 0) endpointsContent += ` pathParams: params,
420
+ `;
421
+ if (action.inputType !== "undefined" && action.inputType !== "QueryOptions") endpointsContent += ` input: body,
422
+ `;
423
+ else if (action.hasQuery) endpointsContent += ` input: query,
424
+ `;
425
+ endpointsContent += ` }),
426
+
427
+ `;
428
+ }
429
+ endpointsContent += `};
430
+ `;
431
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, `${camelCaseModuleName}.endpoints.ts`), endpointsContent.trim());
432
+ console.log(import_chalk.default.gray(` \u2713 ${camelCaseModuleName}.endpoints.ts`));
433
+ const contextFileContent = `// Auto-generated file. Do not edit.
434
+ 'use client';
435
+
436
+ import React from 'react';
437
+ import { createApiModuleContext, useApiModule } from 'api-core-lib/client';
438
+ import { apiClient } from '@/lib/api-core/clientApi';
439
+ import { ${module2.moduleName}, ${module2.moduleName} as TModuleType } from './config';
440
+
441
+ const { Provider, useContext: use${moduleBaseName}Context } = createApiModuleContext<typeof TModuleType['actions']>();
442
+
443
+ export { use${moduleBaseName}Context };
444
+
445
+ type Options = Parameters<typeof useApiModule>[2];
446
+
447
+ interface ${moduleBaseName}ProviderProps {
448
+ children: React.ReactNode;
449
+ options?: Options;
450
+ }
451
+
452
+ export function ${moduleBaseName}Provider({ children, options = {} }: ${moduleBaseName}ProviderProps) {
453
+ const api = useApiModule(apiClient, ${module2.moduleName}, options);
454
+ return <Provider value={api}>{children}</Provider>;
455
+ }`;
456
+ const contextFileName = `${camelCaseModuleName}.context.tsx`;
457
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, contextFileName), contextFileContent.trim());
458
+ console.log(import_chalk.default.gray(` \u2713 ${contextFileName}`));
459
+ const serverHelperContent = `// Auto-generated file. For server-side use only.
460
+
461
+ import { createServerApi } from 'api-core-lib/server';
462
+ import { serverApiClient } from '@/lib/api-core/serverApi';
463
+ import { ${module2.moduleName} } from './config';
464
+
465
+ export const create${moduleBaseName}ServerApi = () => {
466
+ return createServerApi(serverApiClient, ${module2.moduleName});
467
+ };`;
468
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, `${camelCaseModuleName}.server.ts`), serverHelperContent.trim());
469
+ console.log(import_chalk.default.gray(` \u2713 ${camelCaseModuleName}.server.ts`));
470
+ const clientExports = `
471
+ export * from './${camelCaseModuleName}.endpoints';
472
+ export * from './${camelCaseModuleName}.context';`;
473
+ import_fs.default.appendFileSync(indexFilePath, clientExports);
474
+ console.log(import_chalk.default.gray(` \u2713 index.ts (Updated)`));
475
+ const serverEntryPointContent = `// Auto-generated file. For server-side use only.
476
+
477
+ export * from './${camelCaseModuleName}.server';
478
+ export * from './${camelCaseModuleName}.endpoints';`;
479
+ import_fs.default.writeFileSync(import_path.default.join(moduleOutputPath, "server.ts"), serverEntryPointContent);
480
+ console.log(import_chalk.default.gray(` \u2713 server.ts (Server Entry Point)`));
231
481
  }
232
- async function runGeneratorV1(options) {
233
- console.log(import_chalk.default.cyan.bold("\u{1F680} Starting API Development Platform Generator (Godfather Interactive Edition)..."));
482
+ async function runGenerator(options) {
483
+ console.log(import_chalk.default.cyan.bold("\u{1F680} Starting API Development Platform Generator..."));
234
484
  import_dotenv.default.config({ path: options.envPath });
235
485
  const specUrl = process.env.OPENAPI_SPEC_URL || "./swagger.json";
486
+ const prompt = import_inquirer.default.default?.prompt || import_inquirer.default.prompt;
236
487
  try {
237
488
  console.log(import_chalk.default.blue(`
238
489
  \u23F3 Step 1: Dereferencing spec from ${specUrl}...`));
@@ -246,7 +497,7 @@ async function runGeneratorV1(options) {
246
497
  if (import_fs.default.existsSync(outputDir)) {
247
498
  console.log(import_chalk.default.yellow.bold(`
248
499
  \u26A0\uFE0F An existing generation has been found at: ${outputDir}`));
249
- const { action } = await inquirer.prompt([{
500
+ const { action } = await prompt([{
250
501
  type: "list",
251
502
  name: "action",
252
503
  message: "What would you like to do?",
@@ -261,7 +512,7 @@ async function runGeneratorV1(options) {
261
512
  return;
262
513
  }
263
514
  if (action === "full") {
264
- const { confirm } = await inquirer.prompt([{
515
+ const { confirm } = await prompt([{
265
516
  type: "confirm",
266
517
  name: "confirm",
267
518
  message: import_chalk.default.red.bold("Are you sure? This will permanently delete all files in the output directory."),
@@ -287,7 +538,7 @@ async function runGeneratorV1(options) {
287
538
  console.log(import_chalk.default.yellow("No modules found in the spec to update. Exiting."));
288
539
  return;
289
540
  }
290
- const { modulesToRegenerate } = await inquirer.prompt([{
541
+ const { modulesToRegenerate } = await prompt([{
291
542
  type: "checkbox",
292
543
  name: "modulesToRegenerate",
293
544
  message: "Select the modules to generate or update:",
@@ -296,7 +547,7 @@ async function runGeneratorV1(options) {
296
547
  ...existingModulesToUpdate.map((name) => ({ name, value: name, checked: false }))
297
548
  ]
298
549
  }]);
299
- if (modulesToRegenerate.length === 0) {
550
+ if (!modulesToRegenerate || modulesToRegenerate.length === 0) {
300
551
  console.log(import_chalk.default.gray("No modules selected. Operation cancelled."));
301
552
  return;
302
553
  }
@@ -329,6 +580,6 @@ async function runGeneratorV1(options) {
329
580
  console.log("API Core Lib - Code Generator");
330
581
  import_commander.program.option("-o, --output <path>", "Output directory for generated files", "src/lib/api-generated").option("--env-path <path>", ".env file path", import_path2.default.resolve(process.cwd(), ".env")).action((options) => {
331
582
  const absoluteOutputPath = import_path2.default.resolve(process.cwd(), options.output);
332
- runGeneratorV1({ ...options, output: absoluteOutputPath });
583
+ runGenerator({ ...options, output: absoluteOutputPath });
333
584
  });
334
585
  import_commander.program.parse(process.argv);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "api-core-lib",
3
- "version": "12.12.102",
3
+ "version": "12.12.104",
4
4
  "description": "A flexible and powerful API client library for modern web applications.",
5
5
  "type": "module",
6
6
  "exports": {