UNPKG

@sasonarik/nextapi-swagger

Version:

CLI tool to generate Next.js API routes and types from Swagger/OpenAPI specs

68 lines (67 loc) 3.12 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.generateTypes = generateTypes; const fs_extra_1 = __importDefault(require("fs-extra")); const path_1 = __importDefault(require("path")); const helper_1 = require("../helper/helper"); const chalk_1 = __importDefault(require("chalk")); async function generateTypes(spec, outDir, baseName) { const outPath = path_1.default.join(outDir, "types", "api.ts"); await fs_extra_1.default.ensureDir(path_1.default.dirname(outPath)); let existingContent = ""; let existingInterfaceNames = new Set(); // Read existing file content if (await fs_extra_1.default.pathExists(outPath)) { existingContent = await fs_extra_1.default.readFile(outPath, "utf8"); console.log(chalk_1.default.yellow(`ℹ️ Existing file found at ${outPath}`)); // Extract already defined interface names using regex const interfaceRegex = /export\s+interface\s+(\w+)/g; let match; while ((match = interfaceRegex.exec(existingContent)) !== null) { existingInterfaceNames.add(match[1]); } } const lines = []; const seenInterfaces = new Set(); const schemas = spec.components?.schemas ?? spec.definitions ?? {}; if (Object.keys(schemas).length === 0) { console.log(chalk_1.default.yellowBright(`❌ No schemas found in spec. Check OpenAPI version.`)); const fallbackContent = [`// Auto-generated types for ${baseName}`, ``]; await fs_extra_1.default.writeFile(outPath, fallbackContent.join("\n\n")); return; } // Add ApiResult only if it's not already defined if (!existingInterfaceNames.has("ApiResult")) { lines.push(`export interface ApiResult<T> {`, ` status: boolean;`, ` data: T;`, ` message: string;`, `}`, ``); } for (const [rawName, schema] of Object.entries(schemas)) { const name = (0, helper_1.cleanTypeName)(rawName); if (seenInterfaces.has(name) || existingInterfaceNames.has(name)) continue; seenInterfaces.add(name); const props = schema.properties ?? {}; const required = new Set(schema.required ?? []); const typeLines = Object.entries(props).map(([key, val]) => { const optional = required.has(key) ? "" : "?"; const type = (0, helper_1.resolveType)(val); return ` ${key}${optional}: ${type};`; }); lines.push(`export interface ${name} {`, ...typeLines, `}`); } if (lines.length > 0) { const newContent = lines.join("\n\n"); const fullContent = [existingContent, newContent] .filter(Boolean) .join("\n\n"); await fs_extra_1.default.writeFile(outPath, fullContent); console.log(chalk_1.default.greenBright(`✅ API types written to ${outPath}`)); } else { console.log(chalk_1.default.gray(`ℹ️ No new interfaces to write.`)); } }