@geekmidas/cli 10.0.0-alpha.5 → 10.0.0-alpha.6

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 (65) hide show
  1. package/dist/{config-C21ocYNd.cjs → config-CNz5KaSR.cjs} +16 -45
  2. package/dist/config-CNz5KaSR.cjs.map +1 -0
  3. package/dist/{config-WRdsQYZK.mjs → config-CxP7P-qG.mjs} +17 -46
  4. package/dist/config-CxP7P-qG.mjs.map +1 -0
  5. package/dist/config.cjs +2 -2
  6. package/dist/config.d.cts +2 -2
  7. package/dist/config.d.mts +2 -2
  8. package/dist/config.mjs +2 -2
  9. package/dist/{credentials-BBIRJVp4.mjs → credentials-BK3Z93MX.mjs} +5 -5
  10. package/dist/credentials-BK3Z93MX.mjs.map +1 -0
  11. package/dist/{credentials-G1JwBoXH.cjs → credentials-DzsXZzkx.cjs} +5 -5
  12. package/dist/credentials-DzsXZzkx.cjs.map +1 -0
  13. package/dist/discover-CAlFgYec.mjs.map +1 -1
  14. package/dist/discover-DTmFeloL.cjs.map +1 -1
  15. package/dist/{index-BThUzEIp.d.mts → index-BGGdjueF.d.cts} +2 -2
  16. package/dist/index-BGGdjueF.d.cts.map +1 -0
  17. package/dist/{index-CHB4tSzX.d.cts → index-DEbaleny.d.mts} +2 -2
  18. package/dist/index-DEbaleny.d.mts.map +1 -0
  19. package/dist/index.cjs +307 -121
  20. package/dist/index.cjs.map +1 -1
  21. package/dist/index.mjs +307 -121
  22. package/dist/index.mjs.map +1 -1
  23. package/dist/{openapi-kkQbsRVj.mjs → openapi-Bw8DWFWz.mjs} +104 -50
  24. package/dist/openapi-Bw8DWFWz.mjs.map +1 -0
  25. package/dist/{openapi-CA0yJUTN.cjs → openapi-D-dx9Akj.cjs} +122 -50
  26. package/dist/openapi-D-dx9Akj.cjs.map +1 -0
  27. package/dist/openapi.cjs +5 -3
  28. package/dist/openapi.d.cts +46 -10
  29. package/dist/openapi.d.cts.map +1 -1
  30. package/dist/openapi.d.mts +46 -10
  31. package/dist/openapi.d.mts.map +1 -1
  32. package/dist/openapi.mjs +4 -4
  33. package/dist/reconcile/public.d.cts +1 -1
  34. package/dist/reconcile/public.d.mts +1 -1
  35. package/dist/setup-8IWPsRIN.cjs +11 -0
  36. package/dist/{setup-DXvRLTZN.mjs → setup-BWMhbW-p.mjs} +3 -3
  37. package/dist/{setup-DXvRLTZN.mjs.map → setup-BWMhbW-p.mjs.map} +1 -1
  38. package/dist/{setup-Cm2UnAdh.cjs → setup-D7L4BgBT.cjs} +3 -3
  39. package/dist/{setup-Cm2UnAdh.cjs.map → setup-D7L4BgBT.cjs.map} +1 -1
  40. package/dist/{setup-ZijS4qeC.mjs → setup-DGIPd2fh.mjs} +4 -4
  41. package/dist/{types-C-arnQ1r.d.mts → types-BLSNdrk0.d.cts} +5 -13
  42. package/dist/{types-C-arnQ1r.d.mts.map → types-BLSNdrk0.d.cts.map} +1 -1
  43. package/dist/{types-abJQuk7m.d.cts → types-C3POXhw3.d.mts} +2 -10
  44. package/dist/{types-abJQuk7m.d.cts.map → types-C3POXhw3.d.mts.map} +1 -1
  45. package/dist/workspace/index.cjs +1 -1
  46. package/dist/workspace/index.d.cts +2 -2
  47. package/dist/workspace/index.d.mts +2 -2
  48. package/dist/workspace/index.mjs +1 -1
  49. package/dist/{workspace-DdJss8I6.cjs → workspace-CGaUAw5A.cjs} +3 -3
  50. package/dist/workspace-CnTqIlB3.mjs +8 -0
  51. package/dist/{workspace-BFMrAKqI.mjs → workspace-DIuZx-cc.mjs} +1 -17
  52. package/dist/{workspace-BFMrAKqI.mjs.map → workspace-DIuZx-cc.mjs.map} +1 -1
  53. package/dist/{workspace-BcucjwvA.cjs → workspace-LKiNyaDy.cjs} +1 -17
  54. package/dist/{workspace-BcucjwvA.cjs.map → workspace-LKiNyaDy.cjs.map} +1 -1
  55. package/package.json +11 -11
  56. package/dist/config-C21ocYNd.cjs.map +0 -1
  57. package/dist/config-WRdsQYZK.mjs.map +0 -1
  58. package/dist/credentials-BBIRJVp4.mjs.map +0 -1
  59. package/dist/credentials-G1JwBoXH.cjs.map +0 -1
  60. package/dist/index-BThUzEIp.d.mts.map +0 -1
  61. package/dist/index-CHB4tSzX.d.cts.map +0 -1
  62. package/dist/openapi-CA0yJUTN.cjs.map +0 -1
  63. package/dist/openapi-kkQbsRVj.mjs.map +0 -1
  64. package/dist/setup-B5_oHHUj.cjs +0 -11
  65. package/dist/workspace-k4l3rsFh.mjs +0 -8
@@ -1 +0,0 @@
1
- {"version":3,"file":"openapi-kkQbsRVj.mjs","names":["endpoint: Endpoint<\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany\n\t>","features: EndpointFeatures","exportName: string","s: { serviceName: string }","analyses: EndpointAnalysis[]","byTier: Record<EndpointTier, number>","byFeature: Record<keyof EndpointFeatures, number>","exportName: string","features: EndpointFeatures","validators: string[]","analysis: EndpointAnalysis","analyses: EndpointAnalysis[]","exports: string[]","factories: string[]","endpointImport: EndpointImportInfo","tier: 'minimal' | 'standard' | 'full'","calls","imports: string[]","str: string","endpointImports: EndpointImportInfo[]","files: GeneratedEndpointFilesNested","context: BuildContext","fromDir: string","target: string","surface: BuildContext['surface']","value: any","constructs: GeneratedConstruct<\n\t\t\tEndpoint<\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany\n\t\t\t>\n\t\t>[]","outputDir: string","options?: GeneratorOptions","routes: RouteInfo[]","routeInfo: RouteInfo","sourceFile: string","exportName: string","provider: LegacyProvider","_endpoint: Endpoint<\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany\n\t\t>","content: string","endpoints: GeneratedConstruct<\n\t\t\tEndpoint<\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany\n\t\t\t>\n\t\t>[]","endpointsPath: string","_endpointImports: string","_allExportNames: string[]","analyses: EndpointAnalysis[]","endpointImports: EndpointImportInfo[]","importPath: string","drivers?: StorageDrivers","endpoints: Endpoint<any, any, any, any, any, any>[]","options: OpenApiTsOptions","endpointInfos: EndpointInfo[]","type: string","_name: string","authMap: Record<string, string | null>","interfaces: string[]","schema: StandardSchemaV1","defaultName: string","info: EndpointInfo","str: string","name: string","collectedDefs: Map<string, JsonSchema>","schema: JsonSchema","props: string[]","s: JsonSchema","e: string","pathEntries: string[]","methodEntries: string[]","parts: string[]","params: {\n\t\ttitle: string;\n\t\tversion: string;\n\t\tdescription?: string;\n\t\tsecuritySchemes: SecuritySchemeInfo[];\n\t\tendpointAuth: Record<string, string | null>;\n\t\tschemaInterfaces: string;\n\t\tpathsInterface: string;\n\t}","routes: Routes | undefined","config: GkmConfig","options: { silent?: boolean; bustCache?: boolean }","options: OpenAPIOptions","workspaceRoot: string","_appName: string","app: NormalizedAppConfig","gkmConfig: GkmConfig","appCwd: string","appName: string","resolve"],"sources":["../src/build/endpoint-analyzer.ts","../src/build/handler-templates.ts","../src/generators/EndpointGenerator.ts","../src/generators/OpenApiTsGenerator.ts","../src/workspace/client-generator.ts","../src/openapi.ts"],"sourcesContent":["/**\n * Endpoint Analyzer for Build-Time Feature Detection\n *\n * Analyzes endpoints at build time to determine their features and assign\n * optimization tiers. This enables generating specialized handler code\n * for maximum performance.\n */\nimport type { Endpoint } from '@geekmidas/constructs/endpoints';\n\n/**\n * Features detected from an endpoint configuration\n */\nexport interface EndpointFeatures {\n\thasAuth: boolean;\n\thasServices: boolean;\n\thasDatabase: boolean;\n\thasBodyValidation: boolean;\n\thasQueryValidation: boolean;\n\thasParamValidation: boolean;\n\thasAudits: boolean;\n\thasEvents: boolean;\n\thasRateLimit: boolean;\n\thasRls: boolean;\n\thasOutputValidation: boolean;\n}\n\n/**\n * Optimization tiers based on endpoint complexity\n *\n * - minimal: No auth, no services, no audits, no events - near-raw-Hono performance\n * - standard: Some features enabled - uses middleware composition\n * - full: Complex endpoints with many features - full handler chain\n */\nexport type EndpointTier = 'minimal' | 'standard' | 'full';\n\n/**\n * Complete analysis of an endpoint for build-time optimization\n */\nexport interface EndpointAnalysis {\n\troute: string;\n\tmethod: string;\n\texportName: string;\n\tfeatures: EndpointFeatures;\n\ttier: EndpointTier;\n\tserviceNames: string[];\n\tdatabaseServiceName?: string;\n}\n\n/**\n * Analyze an endpoint to extract its features\n */\nexport function analyzeEndpointFeatures(\n\tendpoint: Endpoint<\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany\n\t>,\n): EndpointFeatures {\n\treturn {\n\t\thasAuth: !!endpoint.authorizer,\n\t\thasServices: endpoint.services.length > 0,\n\t\thasDatabase: !!endpoint.databaseService,\n\t\thasBodyValidation: !!endpoint.input?.body,\n\t\thasQueryValidation: !!endpoint.input?.query,\n\t\thasParamValidation: !!endpoint.input?.params,\n\t\t// Only declarative audits (.audit([...])) require full tier with transaction wrapping\n\t\t// Having auditorStorageService just makes auditor available to handler (like other services)\n\t\thasAudits: (endpoint.audits?.length ?? 0) > 0,\n\t\thasEvents: (endpoint.events?.length ?? 0) > 0,\n\t\thasRateLimit: !!endpoint.rateLimit,\n\t\thasRls: !!endpoint.rlsConfig && !endpoint.rlsBypass,\n\t\thasOutputValidation: !!endpoint.outputSchema,\n\t};\n}\n\n/**\n * Determine the optimization tier for an endpoint based on its features\n */\nexport function determineEndpointTier(\n\tfeatures: EndpointFeatures,\n): EndpointTier {\n\tconst {\n\t\thasAuth,\n\t\thasServices,\n\t\thasDatabase,\n\t\thasAudits,\n\t\thasEvents,\n\t\thasRateLimit,\n\t\thasRls,\n\t} = features;\n\n\t// Minimal tier: No complex features\n\t// These endpoints can use near-raw-Hono handlers\n\tif (\n\t\t!hasAuth &&\n\t\t!hasServices &&\n\t\t!hasDatabase &&\n\t\t!hasAudits &&\n\t\t!hasEvents &&\n\t\t!hasRateLimit &&\n\t\t!hasRls\n\t) {\n\t\treturn 'minimal';\n\t}\n\n\t// Full tier: Has audits, RLS, or rate limiting (complex state management)\n\tif (hasAudits || hasRls || hasRateLimit) {\n\t\treturn 'full';\n\t}\n\n\t// Standard tier: Auth and/or services, but no complex state\n\treturn 'standard';\n}\n\n/**\n * Perform complete analysis of an endpoint\n */\nexport function analyzeEndpoint(\n\tendpoint: Endpoint<\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany\n\t>,\n\texportName: string,\n): EndpointAnalysis {\n\tconst features = analyzeEndpointFeatures(endpoint);\n\tconst tier = determineEndpointTier(features);\n\n\treturn {\n\t\troute: endpoint.route,\n\t\tmethod: endpoint.method,\n\t\texportName,\n\t\tfeatures,\n\t\ttier,\n\t\tserviceNames: endpoint.services.map(\n\t\t\t(s: { serviceName: string }) => s.serviceName,\n\t\t),\n\t\tdatabaseServiceName: endpoint.databaseService?.serviceName,\n\t};\n}\n\n/**\n * Analyze multiple endpoints and return analysis results\n */\nexport function analyzeEndpoints(\n\tendpoints: Array<{\n\t\tendpoint: Endpoint<\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany\n\t\t>;\n\t\texportName: string;\n\t}>,\n): EndpointAnalysis[] {\n\treturn endpoints.map(({ endpoint, exportName }) =>\n\t\tanalyzeEndpoint(endpoint, exportName),\n\t);\n}\n\n/**\n * Generate a summary of endpoint analysis for logging\n */\nexport function summarizeAnalysis(analyses: EndpointAnalysis[]): {\n\ttotal: number;\n\tbyTier: Record<EndpointTier, number>;\n\tbyFeature: Record<keyof EndpointFeatures, number>;\n} {\n\tconst byTier: Record<EndpointTier, number> = {\n\t\tminimal: 0,\n\t\tstandard: 0,\n\t\tfull: 0,\n\t};\n\n\tconst byFeature: Record<keyof EndpointFeatures, number> = {\n\t\thasAuth: 0,\n\t\thasServices: 0,\n\t\thasDatabase: 0,\n\t\thasBodyValidation: 0,\n\t\thasQueryValidation: 0,\n\t\thasParamValidation: 0,\n\t\thasAudits: 0,\n\t\thasEvents: 0,\n\t\thasRateLimit: 0,\n\t\thasRls: 0,\n\t\thasOutputValidation: 0,\n\t};\n\n\tfor (const analysis of analyses) {\n\t\tbyTier[analysis.tier]++;\n\n\t\tfor (const [feature, enabled] of Object.entries(analysis.features)) {\n\t\t\tif (enabled) {\n\t\t\t\tbyFeature[feature as keyof EndpointFeatures]++;\n\t\t\t}\n\t\t}\n\t}\n\n\treturn {\n\t\ttotal: analyses.length,\n\t\tbyTier,\n\t\tbyFeature,\n\t};\n}\n","/**\n * Handler Templates for Build-Time Code Generation\n *\n * Generates optimized handler code based on endpoint tier:\n * - minimal: Near-raw-Hono performance for simple endpoints\n * - standard: Middleware composition for auth/services\n * - full: Complete handler chain for complex endpoints\n *\n * Output structure (split by tier):\n * - endpoints/validators.ts - Shared validator factories\n * - endpoints/minimal.ts - Minimal tier handlers\n * - endpoints/standard.ts - Standard tier handlers\n * - endpoints/full.ts - Full tier handlers\n * - endpoints/index.ts - Main entry point\n */\nimport type { EndpointAnalysis, EndpointFeatures } from './endpoint-analyzer';\n\n/**\n * Multi-file output structure (flat by tier)\n */\nexport interface GeneratedEndpointFiles {\n\t'validators.ts': string;\n\t'minimal.ts': string;\n\t'standard.ts': string;\n\t'full.ts': string;\n\t'index.ts': string;\n}\n\n/**\n * Nested folder structure with per-endpoint files\n *\n * Structure:\n * - endpoints/validators.ts\n * - endpoints/minimal/index.ts\n * - endpoints/minimal/[endpointName].ts\n * - endpoints/standard/index.ts\n * - endpoints/standard/[endpointName].ts\n * - endpoints/full/index.ts\n * - endpoints/full/[endpointName].ts\n * - endpoints/index.ts\n */\nexport interface GeneratedEndpointFilesNested {\n\t'validators.ts': string;\n\t'minimal/index.ts': string;\n\t'standard/index.ts': string;\n\t'full/index.ts': string;\n\t'index.ts': string;\n\t[path: string]: string; // e.g., 'minimal/healthEndpoint.ts'\n}\n\n/**\n * Endpoint import info for generating import statements\n */\nexport interface EndpointImportInfo {\n\texportName: string;\n\timportPath: string;\n}\n\n/**\n * Generate imports needed for optimized endpoints file\n */\nexport function generateOptimizedImports(analyses: EndpointAnalysis[]): string {\n\tconst needsValidator = analyses.some(\n\t\t(a) =>\n\t\t\ta.features.hasBodyValidation ||\n\t\t\ta.features.hasQueryValidation ||\n\t\t\ta.features.hasParamValidation,\n\t);\n\n\tconst needsResponseBuilder = analyses.some(\n\t\t(a) => a.tier === 'standard' || a.tier === 'full',\n\t);\n\n\tconst needsServiceDiscovery = analyses.some(\n\t\t(a) => a.features.hasServices || a.features.hasDatabase,\n\t);\n\n\tconst needsEvents = analyses.some((a) => a.features.hasEvents);\n\n\tconst needsAudits = analyses.some((a) => a.features.hasAudits);\n\n\tconst needsRateLimit = analyses.some((a) => a.features.hasRateLimit);\n\n\tconst needsRls = analyses.some((a) => a.features.hasRls);\n\n\tconst imports: string[] = [\n\t\t`import type { EnvironmentParser } from '@geekmidas/envkit';`,\n\t\t`import type { Logger } from '@geekmidas/logger';`,\n\t\t`import type { Hono } from 'hono';`,\n\t];\n\n\tif (needsValidator) {\n\t\timports.push(`import { validator } from 'hono/validator';`);\n\t}\n\n\timports.push(`import { Endpoint } from '@geekmidas/constructs/endpoints';`);\n\n\tif (needsResponseBuilder) {\n\t\timports.push(\n\t\t\t`import { ResponseBuilder } from '@geekmidas/constructs/endpoints';`,\n\t\t);\n\t}\n\n\tif (needsServiceDiscovery) {\n\t\timports.push(`import { ServiceDiscovery } from '@geekmidas/services';`);\n\t}\n\n\tif (needsEvents) {\n\t\timports.push(\n\t\t\t`import { publishConstructEvents } from '@geekmidas/constructs/endpoints';`,\n\t\t);\n\t}\n\n\tif (needsAudits) {\n\t\timports.push(\n\t\t\t`import { createAuditContext, withAuditableEndpointTransaction } from '@geekmidas/constructs/endpoints';`,\n\t\t);\n\t}\n\n\tif (needsRateLimit) {\n\t\timports.push(`import { createError } from '@geekmidas/errors';`);\n\t}\n\n\tif (needsRls) {\n\t\timports.push(\n\t\t\t`import { withRlsContext, extractRlsContext } from '@geekmidas/constructs/endpoints';`,\n\t\t);\n\t}\n\n\treturn imports.join('\\n');\n}\n\n/**\n * Generate reusable validator middleware factories\n */\nexport function generateValidatorFactories(\n\tanalyses: EndpointAnalysis[],\n): string {\n\tconst needsBody = analyses.some((a) => a.features.hasBodyValidation);\n\tconst needsQuery = analyses.some((a) => a.features.hasQueryValidation);\n\tconst needsParams = analyses.some((a) => a.features.hasParamValidation);\n\n\tif (!needsBody && !needsQuery && !needsParams) {\n\t\treturn '';\n\t}\n\n\tconst factories: string[] = [];\n\n\tif (needsBody) {\n\t\tfactories.push(`\nconst validateBody = (endpoint: any) =>\n validator('json', async (value, c) => {\n if (!endpoint.input?.body) return undefined;\n const parsed = await Endpoint.validate(endpoint.input.body, value);\n if (parsed.issues) return c.json(parsed.issues, 422);\n return parsed.value;\n });`);\n\t}\n\n\tif (needsQuery) {\n\t\tfactories.push(`\nconst validateQuery = (endpoint: any) =>\n validator('query', async (_, c) => {\n if (!endpoint.input?.query) return undefined;\n const rawQuery = Object.fromEntries(new URL(c.req.url).searchParams);\n const parsed = await Endpoint.validate(endpoint.input.query, rawQuery);\n if (parsed.issues) return c.json(parsed.issues, 422);\n return parsed.value;\n });`);\n\t}\n\n\tif (needsParams) {\n\t\tfactories.push(`\nconst validateParams = (endpoint: any) =>\n validator('param', async (params, c) => {\n if (!endpoint.input?.params) return undefined;\n const parsed = await Endpoint.validate(endpoint.input.params, params);\n if (parsed.issues) return c.json(parsed.issues, 422);\n return parsed.value;\n });`);\n\t}\n\n\treturn factories.join('\\n');\n}\n\n/**\n * Generate validator references for an endpoint\n */\nfunction generateValidators(\n\texportName: string,\n\tfeatures: EndpointFeatures,\n): string {\n\tconst validators: string[] = [];\n\n\tif (features.hasBodyValidation) {\n\t\tvalidators.push(`validateBody(${exportName})`);\n\t}\n\n\tif (features.hasQueryValidation) {\n\t\tvalidators.push(`validateQuery(${exportName})`);\n\t}\n\n\tif (features.hasParamValidation) {\n\t\tvalidators.push(`validateParams(${exportName})`);\n\t}\n\n\t// Add trailing comma if there are validators (needed before the handler function)\n\treturn validators.length > 0 ? `\\n ${validators.join(',\\n ')},` : '';\n}\n\n/**\n * Generate a minimal handler (near-raw-Hono performance)\n *\n * Used for: Health checks, public endpoints with no services\n */\nexport function generateMinimalHandler(analysis: EndpointAnalysis): string {\n\tconst { exportName, features } = analysis;\n\tconst method = analysis.method.toLowerCase();\n\n\tconst validators = generateValidators(exportName, features);\n\tconst hasValidators = validators.length > 0;\n\n\t// For truly minimal endpoints (no validation), generate inline handler\n\tif (!hasValidators && !features.hasOutputValidation) {\n\t\treturn `\n // Minimal handler: ${analysis.route} (${analysis.method})\n app.${method}('${analysis.route}', async (c) => {\n const result = await ${exportName}.handler(\n {\n services: {},\n logger,\n body: undefined,\n query: undefined,\n params: undefined,\n session: undefined,\n header: Endpoint.createHeaders(c.req.header()),\n cookie: Endpoint.createCookies(c.req.header().cookie),\n auditor: undefined,\n db: undefined,\n } as any,\n { getMetadata: () => ({}) } as any,\n );\n return c.json(result, ${exportName}.status as any);\n });`;\n\t}\n\n\t// With validation but still minimal\n\treturn `\n // Minimal handler with validation: ${analysis.route} (${analysis.method})\n app.${method}('${analysis.route}',${validators}\n async (c) => {\n const result = await ${exportName}.handler(\n {\n services: {},\n logger,\n body: ${features.hasBodyValidation ? \"(c.req.valid as any)('json')\" : 'undefined'},\n query: ${features.hasQueryValidation ? \"(c.req.valid as any)('query')\" : 'undefined'},\n params: ${features.hasParamValidation ? \"(c.req.valid as any)('param')\" : 'undefined'},\n session: undefined,\n header: Endpoint.createHeaders(c.req.header()),\n cookie: Endpoint.createCookies(c.req.header().cookie),\n auditor: undefined,\n db: undefined,\n } as any,\n { getMetadata: () => ({}) } as any,\n );\n ${\n\t\t\t\tfeatures.hasOutputValidation\n\t\t\t\t\t? `const output = await ${exportName}.parseOutput(result);\n return c.json(output, ${exportName}.status as any);`\n\t\t\t\t\t: `return c.json(result, ${exportName}.status as any);`\n\t\t\t}\n }\n );`;\n}\n\n/**\n * Generate a standard handler (auth and/or services)\n *\n * Used for: Authenticated endpoints, endpoints with services\n */\nexport function generateStandardHandler(analysis: EndpointAnalysis): string {\n\tconst { exportName, features } = analysis;\n\tconst method = analysis.method.toLowerCase();\n\n\tconst validators = generateValidators(exportName, features);\n\n\t// Build service resolution code\n\tlet serviceResolution = '';\n\tif (features.hasServices || features.hasDatabase) {\n\t\tserviceResolution = `\n const services = await serviceDiscovery.register(${exportName}.services);\n ${\n\t\t\t\tfeatures.hasDatabase\n\t\t\t\t\t? `const db = ${exportName}.databaseService\n ? (await serviceDiscovery.register([${exportName}.databaseService]) as any)[${exportName}.databaseService.serviceName]\n : undefined;`\n\t\t\t\t\t: 'const db = undefined;'\n\t\t\t}`;\n\t} else {\n\t\tserviceResolution = `\n const services = {};\n const db = undefined;`;\n\t}\n\n\t// Build auth code\n\tlet authCode = '';\n\tif (features.hasAuth) {\n\t\tauthCode = `\n // Authentication\n const session = await ${exportName}.getSession({\n services,\n logger,\n header,\n cookie,\n ...(db !== undefined && { db }),\n } as any);\n\n const isAuthorized = await ${exportName}.authorize({\n header,\n cookie,\n services,\n logger,\n session,\n } as any);\n\n if (!isAuthorized) {\n return c.json({ error: 'Unauthorized' }, 401);\n }`;\n\t}\n\n\t// Build event publishing code\n\tlet eventCode = '';\n\tif (features.hasEvents) {\n\t\teventCode = `\n // Publish events on success\n if (Endpoint.isSuccessStatus(${exportName}.status)) {\n await (publishConstructEvents as any)(\n ${exportName},\n result,\n serviceDiscovery,\n logger,\n );\n }`;\n\t}\n\n\treturn `\n // Standard handler: ${analysis.route} (${analysis.method})\n app.${method}('${analysis.route}',${validators}\n async (c) => {\n const headerValues = c.req.header();\n const header = Endpoint.createHeaders(headerValues);\n const cookie = Endpoint.createCookies(headerValues.cookie);\n${serviceResolution}\n${authCode}\n\n const responseBuilder = new ResponseBuilder();\n const result = await ${exportName}.handler(\n {\n services,\n logger,\n body: ${features.hasBodyValidation ? \"(c.req.valid as any)('json')\" : 'undefined'},\n query: ${features.hasQueryValidation ? \"(c.req.valid as any)('query')\" : 'undefined'},\n params: ${features.hasParamValidation ? \"(c.req.valid as any)('param')\" : 'undefined'},\n session: ${features.hasAuth ? 'session' : 'undefined'},\n header,\n cookie,\n auditor: undefined,\n db,\n } as any,\n responseBuilder,\n );\n\n let data = result;\n let metadata = responseBuilder.getMetadata();\n\n if (Endpoint.hasMetadata(result)) {\n data = result.data;\n metadata = result.metadata;\n }\n\n ${\n\t\t\t\tfeatures.hasOutputValidation\n\t\t\t\t\t? `const output = ${exportName}.outputSchema\n ? await ${exportName}.parseOutput(data)\n : data;`\n\t\t\t\t\t: 'const output = data;'\n\t\t\t}\n${eventCode}\n\n const status = (metadata.status ?? ${exportName}.status) as any;\n return c.json(output, status);\n }\n );`;\n}\n\n/**\n * Generate setup function that uses HonoEndpoint.addRoutes for full-featured endpoints\n * but generates optimized inline handlers for minimal/standard endpoints\n */\nexport function generateOptimizedSetupFunction(\n\tanalyses: EndpointAnalysis[],\n\t_allExportNames: string[],\n): string {\n\tconst minimalEndpoints = analyses.filter((a) => a.tier === 'minimal');\n\tconst standardEndpoints = analyses.filter((a) => a.tier === 'standard');\n\tconst fullEndpoints = analyses.filter((a) => a.tier === 'full');\n\n\t// Generate inline handlers for minimal and standard endpoints\n\tconst minimalHandlers = minimalEndpoints\n\t\t.map((a) => generateMinimalHandler(a))\n\t\t.join('\\n');\n\n\tconst standardHandlers = standardEndpoints\n\t\t.map((a) => generateStandardHandler(a))\n\t\t.join('\\n');\n\n\t// Full endpoints use HonoEndpoint.addRoutes\n\tconst fullEndpointNames = fullEndpoints.map((a) => a.exportName);\n\n\tconst fullEndpointsSetup =\n\t\tfullEndpointNames.length > 0\n\t\t\t? `\n // Full-featured endpoints use HonoEndpoint.addRoutes\n const fullEndpoints = [${fullEndpointNames.join(', ')}];\n HonoEndpoint.addRoutes(fullEndpoints, serviceDiscovery, app, openApiOptions);`\n\t\t\t: '';\n\n\t// Add HonoEndpoint import only if needed\n\tconst honoEndpointImport =\n\t\tfullEndpointNames.length > 0\n\t\t\t? `import { HonoEndpoint } from '@geekmidas/constructs/hono';`\n\t\t\t: '';\n\n\t// Only generate openApiOptions if we have full endpoints that need it\n\tconst openApiOptionsDecl =\n\t\tfullEndpointNames.length > 0\n\t\t\t? `\n const openApiOptions: any = enableOpenApi ? {\n docsPath: '/__docs',\n openApiOptions: {\n title: 'API Documentation',\n version: '1.0.0',\n description: 'Generated API documentation'\n }\n } : { docsPath: false };`\n\t\t\t: '';\n\n\treturn `${honoEndpointImport}\n\nexport async function setupEndpoints(\n app: Hono,\n envParser: EnvironmentParser<any>,\n logger: Logger,\n enableOpenApi: boolean = false,\n): Promise<void> {\n const serviceDiscovery = ServiceDiscovery.getInstance(envParser);\n${openApiOptionsDecl}\n\n // ============================================\n // Minimal handlers (${minimalEndpoints.length} endpoints)\n // Near-raw-Hono performance\n // ============================================\n${minimalHandlers}\n\n // ============================================\n // Standard handlers (${standardEndpoints.length} endpoints)\n // Auth and/or services\n // ============================================\n${standardHandlers}\n${fullEndpointsSetup}\n\n // Add Swagger UI if OpenAPI is enabled\n if (enableOpenApi) {\n try {\n const { swaggerUI } = await import('@hono/swagger-ui');\n app.get('/__docs/ui', swaggerUI({ url: '/__docs' }));\n } catch {\n // @hono/swagger-ui not installed, skip Swagger UI\n }\n }\n}`;\n}\n\n/**\n * Generate complete optimized endpoints file\n */\nexport function generateOptimizedEndpointsFile(\n\tanalyses: EndpointAnalysis[],\n\tendpointImports: string,\n\tallExportNames: string[],\n): string {\n\tconst imports = generateOptimizedImports(analyses);\n\tconst validatorFactories = generateValidatorFactories(analyses);\n\tconst setupFunction = generateOptimizedSetupFunction(\n\t\tanalyses,\n\t\tallExportNames,\n\t);\n\n\treturn `/**\n * Generated optimized endpoints file\n *\n * Build-time optimization tiers:\n * - minimal: ${analyses.filter((a) => a.tier === 'minimal').length} endpoints (near-raw-Hono)\n * - standard: ${analyses.filter((a) => a.tier === 'standard').length} endpoints (auth/services)\n * - full: ${analyses.filter((a) => a.tier === 'full').length} endpoints (audits/rls/rate-limit)\n */\n${imports}\n${endpointImports}\n${validatorFactories}\n\n${setupFunction}\n`;\n}\n\n// ============================================================================\n// Multi-File Generation (Split by Tier)\n// ============================================================================\n\n/**\n * Generate validators.ts - Shared validator middleware factories\n */\nfunction generateValidatorsFile(analyses: EndpointAnalysis[]): string {\n\tconst needsBody = analyses.some((a) => a.features.hasBodyValidation);\n\tconst needsQuery = analyses.some((a) => a.features.hasQueryValidation);\n\tconst needsParams = analyses.some((a) => a.features.hasParamValidation);\n\n\tif (!needsBody && !needsQuery && !needsParams) {\n\t\treturn `// No validators needed for this build\\nexport {};\\n`;\n\t}\n\n\tconst exports: string[] = [];\n\tconst factories: string[] = [];\n\n\tif (needsBody) {\n\t\texports.push('validateBody');\n\t\tfactories.push(`\nexport const validateBody = (endpoint: any) =>\n validator('json', async (value, c) => {\n if (!endpoint.input?.body) return undefined;\n const parsed = await Endpoint.validate(endpoint.input.body, value);\n if (parsed.issues) return c.json(parsed.issues, 422);\n return parsed.value;\n });`);\n\t}\n\n\tif (needsQuery) {\n\t\texports.push('validateQuery');\n\t\tfactories.push(`\nexport const validateQuery = (endpoint: any) =>\n validator('query', async (_, c) => {\n if (!endpoint.input?.query) return undefined;\n const rawQuery = Object.fromEntries(new URL(c.req.url).searchParams);\n const parsed = await Endpoint.validate(endpoint.input.query, rawQuery);\n if (parsed.issues) return c.json(parsed.issues, 422);\n return parsed.value;\n });`);\n\t}\n\n\tif (needsParams) {\n\t\texports.push('validateParams');\n\t\tfactories.push(`\nexport const validateParams = (endpoint: any) =>\n validator('param', async (params, c) => {\n if (!endpoint.input?.params) return undefined;\n const parsed = await Endpoint.validate(endpoint.input.params, params);\n if (parsed.issues) return c.json(parsed.issues, 422);\n return parsed.value;\n });`);\n\t}\n\n\treturn `/**\n * Generated validator middleware factories\n * Shared across all endpoint tiers that need validation\n */\nimport { validator } from 'hono/validator';\nimport { Endpoint } from '@geekmidas/constructs/endpoints';\n${factories.join('\\n')}\n`;\n}\n\n/**\n * Generate minimal.ts - Minimal tier handlers\n */\nfunction generateMinimalFile(\n\tanalyses: EndpointAnalysis[],\n\tendpointImports: EndpointImportInfo[],\n): string {\n\tconst minimalEndpoints = analyses.filter((a) => a.tier === 'minimal');\n\n\tif (minimalEndpoints.length === 0) {\n\t\treturn `// No minimal-tier endpoints in this build\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\n\nexport function setupMinimalEndpoints(\n _app: Hono,\n _logger: Logger,\n): void {\n // No minimal endpoints\n}\n`;\n\t}\n\n\tconst minimalExportNames = minimalEndpoints.map((a) => a.exportName);\n\tconst relevantImports = endpointImports.filter((i) =>\n\t\tminimalExportNames.includes(i.exportName),\n\t);\n\n\tconst importStatements = relevantImports\n\t\t.map((i) => `import { ${i.exportName} } from '${i.importPath}';`)\n\t\t.join('\\n');\n\n\tconst needsValidators = minimalEndpoints.some(\n\t\t(a) =>\n\t\t\ta.features.hasBodyValidation ||\n\t\t\ta.features.hasQueryValidation ||\n\t\t\ta.features.hasParamValidation,\n\t);\n\n\tconst validatorImport = needsValidators\n\t\t? generateValidatorImports(minimalEndpoints)\n\t\t: '';\n\n\tconst handlers = minimalEndpoints\n\t\t.map((a) => generateMinimalHandler(a))\n\t\t.join('\\n');\n\n\treturn `/**\n * Minimal-tier endpoint handlers (${minimalEndpoints.length} endpoints)\n * Near-raw-Hono performance - no auth, no services, no complex features\n */\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\nimport { Endpoint } from '@geekmidas/constructs/endpoints';\n${validatorImport}\n${importStatements}\n\nexport function setupMinimalEndpoints(\n app: Hono,\n logger: Logger,\n): void {\n${handlers}\n}\n`;\n}\n\n/**\n * Generate standard.ts - Standard tier handlers\n */\nfunction generateStandardFile(\n\tanalyses: EndpointAnalysis[],\n\tendpointImports: EndpointImportInfo[],\n): string {\n\tconst standardEndpoints = analyses.filter((a) => a.tier === 'standard');\n\n\tif (standardEndpoints.length === 0) {\n\t\treturn `// No standard-tier endpoints in this build\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\nimport type { ServiceDiscovery } from '@geekmidas/services';\n\nexport function setupStandardEndpoints(\n _app: Hono,\n _serviceDiscovery: ServiceDiscovery<any, any>,\n _logger: Logger,\n): void {\n // No standard endpoints\n}\n`;\n\t}\n\n\tconst standardExportNames = standardEndpoints.map((a) => a.exportName);\n\tconst relevantImports = endpointImports.filter((i) =>\n\t\tstandardExportNames.includes(i.exportName),\n\t);\n\n\tconst importStatements = relevantImports\n\t\t.map((i) => `import { ${i.exportName} } from '${i.importPath}';`)\n\t\t.join('\\n');\n\n\tconst needsValidators = standardEndpoints.some(\n\t\t(a) =>\n\t\t\ta.features.hasBodyValidation ||\n\t\t\ta.features.hasQueryValidation ||\n\t\t\ta.features.hasParamValidation,\n\t);\n\n\tconst validatorImport = needsValidators\n\t\t? generateValidatorImports(standardEndpoints)\n\t\t: '';\n\n\tconst needsEvents = standardEndpoints.some((a) => a.features.hasEvents);\n\tconst eventsImport = needsEvents\n\t\t? `import { publishConstructEvents } from '@geekmidas/constructs/endpoints';`\n\t\t: '';\n\n\tconst handlers = standardEndpoints\n\t\t.map((a) => generateStandardHandler(a))\n\t\t.join('\\n');\n\n\treturn `/**\n * Standard-tier endpoint handlers (${standardEndpoints.length} endpoints)\n * Auth and/or services enabled, but no complex features like audits/RLS\n */\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\nimport type { ServiceDiscovery } from '@geekmidas/services';\nimport { Endpoint, ResponseBuilder } from '@geekmidas/constructs/endpoints';\n${eventsImport}\n${validatorImport}\n${importStatements}\n\nexport function setupStandardEndpoints(\n app: Hono,\n serviceDiscovery: ServiceDiscovery<any, any>,\n logger: Logger,\n): void {\n${handlers}\n}\n`;\n}\n\n/**\n * Generate full.ts - Full tier handlers (uses HonoEndpoint.addRoutes)\n */\nfunction generateFullFile(\n\tanalyses: EndpointAnalysis[],\n\tendpointImports: EndpointImportInfo[],\n): string {\n\tconst fullEndpoints = analyses.filter((a) => a.tier === 'full');\n\n\tif (fullEndpoints.length === 0) {\n\t\treturn `// No full-tier endpoints in this build\nimport type { Hono } from 'hono';\nimport type { ServiceDiscovery } from '@geekmidas/services';\n\nexport function setupFullEndpoints(\n _app: Hono,\n _serviceDiscovery: ServiceDiscovery<any, any>,\n _enableOpenApi: boolean,\n): void {\n // No full endpoints\n}\n`;\n\t}\n\n\tconst fullExportNames = fullEndpoints.map((a) => a.exportName);\n\tconst relevantImports = endpointImports.filter((i) =>\n\t\tfullExportNames.includes(i.exportName),\n\t);\n\n\tconst importStatements = relevantImports\n\t\t.map((i) => `import { ${i.exportName} } from '${i.importPath}';`)\n\t\t.join('\\n');\n\n\treturn `/**\n * Full-tier endpoint handlers (${fullEndpoints.length} endpoints)\n * Complex features: audits, RLS, rate limiting\n * Uses HonoEndpoint.addRoutes for full feature support\n */\nimport type { Hono } from 'hono';\nimport type { ServiceDiscovery } from '@geekmidas/services';\nimport { HonoEndpoint } from '@geekmidas/constructs/hono';\n${importStatements}\n\nconst fullEndpoints = [${fullExportNames.join(', ')}];\n\nexport function setupFullEndpoints(\n app: Hono,\n serviceDiscovery: ServiceDiscovery<any, any>,\n enableOpenApi: boolean,\n): void {\n const openApiOptions: any = enableOpenApi ? {\n docsPath: '/__docs',\n openApiOptions: {\n title: 'API Documentation',\n version: '1.0.0',\n description: 'Generated API documentation'\n }\n } : { docsPath: false };\n\n HonoEndpoint.addRoutes(fullEndpoints as any, serviceDiscovery, app, openApiOptions);\n}\n`;\n}\n\n/**\n * Generate index.ts - Main entry point\n */\nfunction generateIndexFile(analyses: EndpointAnalysis[]): string {\n\tconst minimalCount = analyses.filter((a) => a.tier === 'minimal').length;\n\tconst standardCount = analyses.filter((a) => a.tier === 'standard').length;\n\tconst fullCount = analyses.filter((a) => a.tier === 'full').length;\n\n\treturn `/**\n * Generated optimized endpoints\n *\n * Build-time optimization tiers:\n * - minimal: ${minimalCount} endpoints (near-raw-Hono)\n * - standard: ${standardCount} endpoints (auth/services)\n * - full: ${fullCount} endpoints (audits/rls/rate-limit)\n */\nimport type { EnvironmentParser } from '@geekmidas/envkit';\nimport type { Logger } from '@geekmidas/logger';\nimport type { Hono } from 'hono';\nimport { ServiceDiscovery } from '@geekmidas/services';\nimport { setupMinimalEndpoints } from './minimal.js';\nimport { setupStandardEndpoints } from './standard.js';\nimport { setupFullEndpoints } from './full.js';\n\nexport async function setupEndpoints(\n app: Hono,\n envParser: EnvironmentParser<any>,\n logger: Logger,\n enableOpenApi: boolean = false,\n): Promise<void> {\n const serviceDiscovery = ServiceDiscovery.getInstance(envParser);\n\n // Minimal handlers (${minimalCount} endpoints) - near-raw-Hono performance\n setupMinimalEndpoints(app, logger);\n\n // Standard handlers (${standardCount} endpoints) - auth/services\n setupStandardEndpoints(app, serviceDiscovery, logger);\n\n // Full handlers (${fullCount} endpoints) - audits/rls/rate-limit\n setupFullEndpoints(app, serviceDiscovery, enableOpenApi);\n\n // Add Swagger UI if OpenAPI is enabled\n if (enableOpenApi) {\n try {\n const { swaggerUI } = await import('@hono/swagger-ui');\n app.get('/__docs/ui', swaggerUI({ url: '/__docs' }));\n } catch {\n // @hono/swagger-ui not installed, skip Swagger UI\n }\n }\n}\n`;\n}\n\n/**\n * Generate validator imports based on what's needed\n */\nfunction generateValidatorImports(analyses: EndpointAnalysis[]): string {\n\tconst needsBody = analyses.some((a) => a.features.hasBodyValidation);\n\tconst needsQuery = analyses.some((a) => a.features.hasQueryValidation);\n\tconst needsParams = analyses.some((a) => a.features.hasParamValidation);\n\n\tconst imports: string[] = [];\n\tif (needsBody) imports.push('validateBody');\n\tif (needsQuery) imports.push('validateQuery');\n\tif (needsParams) imports.push('validateParams');\n\n\tif (imports.length === 0) return '';\n\treturn `import { ${imports.join(', ')} } from './validators.js';`;\n}\n\n/**\n * Generate all endpoint files split by tier (flat structure)\n */\nexport function generateEndpointFilesByTier(\n\tanalyses: EndpointAnalysis[],\n\tendpointImports: EndpointImportInfo[],\n): GeneratedEndpointFiles {\n\treturn {\n\t\t'validators.ts': generateValidatorsFile(analyses),\n\t\t'minimal.ts': generateMinimalFile(analyses, endpointImports),\n\t\t'standard.ts': generateStandardFile(analyses, endpointImports),\n\t\t'full.ts': generateFullFile(analyses, endpointImports),\n\t\t'index.ts': generateIndexFile(analyses),\n\t};\n}\n\n// ============================================================================\n// Per-Endpoint File Generation (Nested Folder Structure)\n// ============================================================================\n\n/**\n * Generate a standalone minimal endpoint file\n */\nfunction generateMinimalEndpointFile(\n\tanalysis: EndpointAnalysis,\n\tendpointImport: EndpointImportInfo,\n): string {\n\tconst { exportName, features } = analysis;\n\n\tconst needsValidators =\n\t\tfeatures.hasBodyValidation ||\n\t\tfeatures.hasQueryValidation ||\n\t\tfeatures.hasParamValidation;\n\n\tconst validatorImport = needsValidators\n\t\t? generateValidatorImportsForEndpoint(analysis)\n\t\t: '';\n\n\tconst handler = generateMinimalHandler(analysis);\n\n\treturn `/**\n * Minimal endpoint: ${analysis.route} (${analysis.method})\n * Near-raw-Hono performance\n */\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\nimport { Endpoint } from '@geekmidas/constructs/endpoints';\n${validatorImport}\nimport { ${exportName} } from '${endpointImport.importPath}';\n\nexport function setup${capitalize(exportName)}(\n app: Hono,\n logger: Logger,\n): void {\n${handler}\n}\n`;\n}\n\n/**\n * Generate a standalone standard endpoint file\n */\nfunction generateStandardEndpointFile(\n\tanalysis: EndpointAnalysis,\n\tendpointImport: EndpointImportInfo,\n): string {\n\tconst { exportName, features } = analysis;\n\n\tconst needsValidators =\n\t\tfeatures.hasBodyValidation ||\n\t\tfeatures.hasQueryValidation ||\n\t\tfeatures.hasParamValidation;\n\n\tconst validatorImport = needsValidators\n\t\t? generateValidatorImportsForEndpoint(analysis)\n\t\t: '';\n\n\tconst eventsImport = features.hasEvents\n\t\t? `import { publishConstructEvents } from '@geekmidas/constructs/endpoints';`\n\t\t: '';\n\n\tconst handler = generateStandardHandler(analysis);\n\n\treturn `/**\n * Standard endpoint: ${analysis.route} (${analysis.method})\n * Auth and/or services enabled\n */\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\nimport type { ServiceDiscovery } from '@geekmidas/services';\nimport { Endpoint, ResponseBuilder } from '@geekmidas/constructs/endpoints';\n${eventsImport}\n${validatorImport}\nimport { ${exportName} } from '${endpointImport.importPath}';\n\nexport function setup${capitalize(exportName)}(\n app: Hono,\n serviceDiscovery: ServiceDiscovery<any, any>,\n logger: Logger,\n): void {\n${handler}\n}\n`;\n}\n\n/**\n * Generate a standalone full endpoint file\n */\nfunction generateFullEndpointFile(\n\tanalysis: EndpointAnalysis,\n\tendpointImport: EndpointImportInfo,\n): string {\n\tconst { exportName } = analysis;\n\n\treturn `/**\n * Full endpoint: ${analysis.route} (${analysis.method})\n * Complex features: audits, RLS, rate limiting\n */\nimport type { Hono } from 'hono';\nimport type { ServiceDiscovery } from '@geekmidas/services';\nimport { HonoEndpoint } from '@geekmidas/constructs/hono';\nimport { ${exportName} } from '${endpointImport.importPath}';\n\nexport function setup${capitalize(exportName)}(\n app: Hono,\n serviceDiscovery: ServiceDiscovery<any, any>,\n openApiOptions: any,\n): void {\n HonoEndpoint.addRoutes([${exportName}] as any, serviceDiscovery, app, openApiOptions);\n}\n`;\n}\n\n/**\n * Generate tier index file that imports and calls all endpoint setup functions\n */\nfunction generateTierIndexFile(\n\ttier: 'minimal' | 'standard' | 'full',\n\tanalyses: EndpointAnalysis[],\n): string {\n\tconst tierEndpoints = analyses.filter((a) => a.tier === tier);\n\n\tif (tierEndpoints.length === 0) {\n\t\tif (tier === 'minimal') {\n\t\t\treturn `// No minimal-tier endpoints in this build\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\n\nexport function setupMinimalEndpoints(\n _app: Hono,\n _logger: Logger,\n): void {\n // No minimal endpoints\n}\n`;\n\t\t}\n\t\tif (tier === 'standard') {\n\t\t\treturn `// No standard-tier endpoints in this build\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\nimport type { ServiceDiscovery } from '@geekmidas/services';\n\nexport function setupStandardEndpoints(\n _app: Hono,\n _serviceDiscovery: ServiceDiscovery<any, any>,\n _logger: Logger,\n): void {\n // No standard endpoints\n}\n`;\n\t\t}\n\t\t// full\n\t\treturn `// No full-tier endpoints in this build\nimport type { Hono } from 'hono';\nimport type { ServiceDiscovery } from '@geekmidas/services';\n\nexport function setupFullEndpoints(\n _app: Hono,\n _serviceDiscovery: ServiceDiscovery<any, any>,\n _enableOpenApi: boolean,\n): void {\n // No full endpoints\n}\n`;\n\t}\n\n\tconst imports = tierEndpoints\n\t\t.map(\n\t\t\t(a) =>\n\t\t\t\t`import { setup${capitalize(a.exportName)} } from './${a.exportName}.js';`,\n\t\t)\n\t\t.join('\\n');\n\n\tif (tier === 'minimal') {\n\t\tconst calls = tierEndpoints\n\t\t\t.map((a) => ` setup${capitalize(a.exportName)}(app, logger);`)\n\t\t\t.join('\\n');\n\n\t\treturn `/**\n * Minimal-tier endpoint index (${tierEndpoints.length} endpoints)\n * Near-raw-Hono performance\n */\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\n${imports}\n\nexport function setupMinimalEndpoints(\n app: Hono,\n logger: Logger,\n): void {\n${calls}\n}\n`;\n\t}\n\n\tif (tier === 'standard') {\n\t\tconst calls = tierEndpoints\n\t\t\t.map(\n\t\t\t\t(a) =>\n\t\t\t\t\t` setup${capitalize(a.exportName)}(app, serviceDiscovery, logger);`,\n\t\t\t)\n\t\t\t.join('\\n');\n\n\t\treturn `/**\n * Standard-tier endpoint index (${tierEndpoints.length} endpoints)\n * Auth and/or services enabled\n */\nimport type { Hono } from 'hono';\nimport type { Logger } from '@geekmidas/logger';\nimport type { ServiceDiscovery } from '@geekmidas/services';\n${imports}\n\nexport function setupStandardEndpoints(\n app: Hono,\n serviceDiscovery: ServiceDiscovery<any, any>,\n logger: Logger,\n): void {\n${calls}\n}\n`;\n\t}\n\n\t// full\n\tconst calls = tierEndpoints\n\t\t.map(\n\t\t\t(a) =>\n\t\t\t\t` setup${capitalize(a.exportName)}(app, serviceDiscovery, openApiOptions);`,\n\t\t)\n\t\t.join('\\n');\n\n\treturn `/**\n * Full-tier endpoint index (${tierEndpoints.length} endpoints)\n * Complex features: audits, RLS, rate limiting\n */\nimport type { Hono } from 'hono';\nimport type { ServiceDiscovery } from '@geekmidas/services';\n${imports}\n\nexport function setupFullEndpoints(\n app: Hono,\n serviceDiscovery: ServiceDiscovery<any, any>,\n enableOpenApi: boolean,\n): void {\n const openApiOptions: any = enableOpenApi ? {\n docsPath: '/__docs',\n openApiOptions: {\n title: 'API Documentation',\n version: '1.0.0',\n description: 'Generated API documentation'\n }\n } : { docsPath: false };\n\n${calls}\n}\n`;\n}\n\n/**\n * Generate validator imports for a single endpoint\n */\nfunction generateValidatorImportsForEndpoint(\n\tanalysis: EndpointAnalysis,\n): string {\n\tconst imports: string[] = [];\n\tif (analysis.features.hasBodyValidation) imports.push('validateBody');\n\tif (analysis.features.hasQueryValidation) imports.push('validateQuery');\n\tif (analysis.features.hasParamValidation) imports.push('validateParams');\n\n\tif (imports.length === 0) return '';\n\treturn `import { ${imports.join(', ')} } from '../validators.js';`;\n}\n\n/**\n * Capitalize first letter\n */\nfunction capitalize(str: string): string {\n\treturn str.charAt(0).toUpperCase() + str.slice(1);\n}\n\n/**\n * Generate all endpoint files with nested folder structure (per-endpoint files)\n */\nexport function generateEndpointFilesNested(\n\tanalyses: EndpointAnalysis[],\n\tendpointImports: EndpointImportInfo[],\n): GeneratedEndpointFilesNested {\n\tconst files: GeneratedEndpointFilesNested = {\n\t\t'validators.ts': generateValidatorsFile(analyses),\n\t\t'minimal/index.ts': generateTierIndexFile('minimal', analyses),\n\t\t'standard/index.ts': generateTierIndexFile('standard', analyses),\n\t\t'full/index.ts': generateTierIndexFile('full', analyses),\n\t\t'index.ts': generateNestedIndexFile(analyses),\n\t};\n\n\t// Generate individual endpoint files\n\tfor (const analysis of analyses) {\n\t\tconst endpointImport = endpointImports.find(\n\t\t\t(i) => i.exportName === analysis.exportName,\n\t\t);\n\t\tif (!endpointImport) continue;\n\n\t\tconst fileName = `${analysis.tier}/${analysis.exportName}.ts`;\n\n\t\tswitch (analysis.tier) {\n\t\t\tcase 'minimal':\n\t\t\t\tfiles[fileName] = generateMinimalEndpointFile(analysis, endpointImport);\n\t\t\t\tbreak;\n\t\t\tcase 'standard':\n\t\t\t\tfiles[fileName] = generateStandardEndpointFile(\n\t\t\t\t\tanalysis,\n\t\t\t\t\tendpointImport,\n\t\t\t\t);\n\t\t\t\tbreak;\n\t\t\tcase 'full':\n\t\t\t\tfiles[fileName] = generateFullEndpointFile(analysis, endpointImport);\n\t\t\t\tbreak;\n\t\t}\n\t}\n\n\treturn files;\n}\n\n/**\n * Generate index.ts for nested structure\n */\nfunction generateNestedIndexFile(analyses: EndpointAnalysis[]): string {\n\tconst minimalCount = analyses.filter((a) => a.tier === 'minimal').length;\n\tconst standardCount = analyses.filter((a) => a.tier === 'standard').length;\n\tconst fullCount = analyses.filter((a) => a.tier === 'full').length;\n\n\treturn `/**\n * Generated optimized endpoints\n *\n * Build-time optimization tiers:\n * - minimal: ${minimalCount} endpoints (near-raw-Hono)\n * - standard: ${standardCount} endpoints (auth/services)\n * - full: ${fullCount} endpoints (audits/rls/rate-limit)\n */\nimport type { EnvironmentParser } from '@geekmidas/envkit';\nimport type { Logger } from '@geekmidas/logger';\nimport type { Hono } from 'hono';\nimport { ServiceDiscovery } from '@geekmidas/services';\nimport { setupMinimalEndpoints } from './minimal/index.js';\nimport { setupStandardEndpoints } from './standard/index.js';\nimport { setupFullEndpoints } from './full/index.js';\n\nexport async function setupEndpoints(\n app: Hono,\n envParser: EnvironmentParser<any>,\n logger: Logger,\n enableOpenApi: boolean = false,\n): Promise<void> {\n const serviceDiscovery = ServiceDiscovery.getInstance(envParser);\n\n // Minimal handlers (${minimalCount} endpoints) - near-raw-Hono performance\n setupMinimalEndpoints(app, logger);\n\n // Standard handlers (${standardCount} endpoints) - auth/services\n setupStandardEndpoints(app, serviceDiscovery, logger);\n\n // Full handlers (${fullCount} endpoints) - audits/rls/rate-limit\n setupFullEndpoints(app, serviceDiscovery, enableOpenApi);\n\n // Add Swagger UI if OpenAPI is enabled\n if (enableOpenApi) {\n try {\n const { swaggerUI } = await import('@hono/swagger-ui');\n app.get('/__docs/ui', swaggerUI({ url: '/__docs' }));\n } catch {\n // @hono/swagger-ui not installed, skip Swagger UI\n }\n }\n}\n`;\n}\n","import { mkdir, writeFile } from 'node:fs/promises';\nimport { dirname, join, relative } from 'node:path';\nimport { Endpoint } from '@geekmidas/constructs/endpoints';\nimport {\n\tanalyzeEndpoint,\n\ttype EndpointAnalysis,\n\tsummarizeAnalysis,\n} from '../build/endpoint-analyzer';\nimport {\n\ttype EndpointImportInfo,\n\tgenerateEndpointFilesNested,\n} from '../build/handler-templates';\nimport type { BuildContext } from '../build/types';\nimport type { LegacyProvider, RouteInfo } from '../types';\nimport type { StorageDrivers } from './drivers';\nimport {\n\tConstructGenerator,\n\ttype GeneratedConstruct,\n\ttype GeneratorOptions,\n} from './Generator';\n\n/**\n * How a generated entry gets its logger and environment parser.\n *\n * From the surface it serves, when there is one: the surface holds both as\n * *objects*, and discovery already recorded which module declares it, so the\n * entry imports that module and reads them off it.\n *\n * The alternative — the shape this replaces — was naming both in config as\n * module paths, `envParser: './config/env#envParser'`, and printing an import\n * for each. Two strings per app, checked by nothing, describing files the\n * surface was already holding the contents of.\n *\n * Falls back to the configured paths for an app that declares no surface.\n */\nexport function runtimeFor(\n\tcontext: BuildContext,\n\tfromDir: string,\n): { imports: string; bindings: string } {\n\tconst module = context.surface?.module;\n\n\tif (module) {\n\t\tconst specifier = importSpecifier(fromDir, module.specifier);\n\n\t\t// Bound to the same names the rest of the entry already uses, so what\n\t\t// changes is where they come from and nothing else.\n\t\treturn {\n\t\t\timports: `import { ${module.exportName} as __surface } from '${specifier}';`,\n\t\t\tbindings: [\n\t\t\t\t'// What this surface was declared with. Objects, not module paths:',\n\t\t\t\t'// the entry imports the surface, so there is nothing to print.',\n\t\t\t\t'const envParser = __surface.envParser;',\n\t\t\t\t'const logger = __surface.logger;',\n\t\t\t].join('\\n'),\n\t\t};\n\t}\n\n\treturn {\n\t\timports: [\n\t\t\t`import ${context.envParserImportPattern} from '${importSpecifier(fromDir, context.envParserPath)}';`,\n\t\t\t`import ${context.loggerImportPattern} from '${importSpecifier(fromDir, context.loggerPath)}';`,\n\t\t].join('\\n'),\n\t\tbindings: '',\n\t};\n}\n\n/** A relative specifier ESM will accept: always prefixed, never bare. */\nfunction importSpecifier(fromDir: string, target: string): string {\n\tconst rel = relative(fromDir, target).replace(/\\.ts$/, '.js');\n\n\treturn rel.startsWith('.') ? rel : `./${rel}`;\n}\n\n/**\n * CORS for a surface, derived rather than hand-written.\n *\n * Who may call a surface is already in the graph — every construct that\n * declared an edge to it — and reaches the process as one comma-separated\n * value. An application that maintained this by hand maintained a list that was\n * wrong in two directions at once: it trusted origins nothing was serving, and\n * it could not name hosts a deploy had not chosen yet.\n *\n * Only the parts a graph cannot answer are configurable, and every one has a\n * default: a surface that says nothing about CORS still gets it.\n */\nexport function corsFor(surface: BuildContext['surface']): {\n\timports: string;\n\tsetup: string;\n} {\n\tif (!surface) return { imports: '', setup: '' };\n\n\tconst cors = surface.cors ?? {};\n\tconst allowHeaders = [\n\t\t'content-type',\n\t\t'authorization',\n\t\t...(cors.allowHeaders ?? []),\n\t];\n\n\treturn {\n\t\timports: `import { cors } from 'hono/cors';`,\n\t\tsetup: `\n // Who may call ${surface.id}, read off the graph rather than listed here.\n {\n const { origins } = envParser\n .create((get) => ({\n origins: get('${surface.trustedOriginsKey}')\n .string()\n .default('')\n .transform((value: string) =>\n value.split(',').map((origin) => origin.trim()).filter(Boolean),\n ),\n }))\n .parse();\n\n honoApp.use('*', cors({\n origin: origins,\n allowMethods: ['GET', 'POST', 'PUT', 'DELETE', 'PATCH', 'OPTIONS'],\n allowHeaders: ${JSON.stringify(allowHeaders)},${\n\t\t\t\tcors.exposeHeaders\n\t\t\t\t\t? `\\n exposeHeaders: ${JSON.stringify(cors.exposeHeaders)},`\n\t\t\t\t\t: ''\n\t\t\t}\n credentials: ${cors.credentials ?? true},\n maxAge: ${cors.maxAge ?? 86400},\n }));\n }\n`,\n\t};\n}\n\nexport class EndpointGenerator extends ConstructGenerator<\n\tEndpoint<\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany\n\t>,\n\tRouteInfo[]\n> {\n\tisConstruct(\n\t\tvalue: any,\n\t): value is Endpoint<\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany,\n\t\tany\n\t> {\n\t\treturn Endpoint.isEndpoint(value);\n\t}\n\n\tasync build(\n\t\tcontext: BuildContext,\n\t\tconstructs: GeneratedConstruct<\n\t\t\tEndpoint<\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany\n\t\t\t>\n\t\t>[],\n\t\toutputDir: string,\n\t\toptions?: GeneratorOptions,\n\t): Promise<RouteInfo[]> {\n\t\tconst provider = options?.provider || 'aws-apigatewayv2';\n\t\tconst enableOpenApi = options?.enableOpenApi || false;\n\t\tconst logger = console;\n\t\tconst routes: RouteInfo[] = [];\n\n\t\tif (constructs.length === 0) {\n\t\t\treturn routes;\n\t\t}\n\n\t\tif (provider === 'server') {\n\t\t\t// Generate endpoints.ts and app.ts\n\t\t\tawait this.generateEndpointsFile(outputDir, constructs, context);\n\t\t\tconst appFile = await this.generateAppFile(outputDir, context);\n\n\t\t\troutes.push({\n\t\t\t\tpath: '*',\n\t\t\t\tmethod: 'ALL',\n\t\t\t\thandler: relative(process.cwd(), appFile),\n\t\t\t\tauthorizer: 'none',\n\t\t\t});\n\n\t\t\tlogger.log(\n\t\t\t\t`Generated server with ${constructs.length} endpoints${enableOpenApi ? ' (OpenAPI enabled)' : ''}`,\n\t\t\t);\n\t\t} else if (provider === 'aws-lambda') {\n\t\t\t// For aws-lambda, create routes subdirectory\n\t\t\tconst routesDir = join(outputDir, 'routes');\n\t\t\tawait mkdir(routesDir, { recursive: true });\n\n\t\t\t// Generate individual handlers for API Gateway routes\n\t\t\tfor (const { key, construct, path } of constructs) {\n\t\t\t\tconst handlerFile = await this.generateHandlerFile(\n\t\t\t\t\troutesDir,\n\t\t\t\t\tpath.relative,\n\t\t\t\t\tkey,\n\t\t\t\t\t'aws-apigatewayv2',\n\t\t\t\t\tconstruct,\n\t\t\t\t\tcontext,\n\t\t\t\t);\n\n\t\t\t\tconst routeInfo: RouteInfo = {\n\t\t\t\t\tpath: construct._path,\n\t\t\t\t\tmethod: construct.method,\n\t\t\t\t\thandler: relative(process.cwd(), handlerFile).replace(\n\t\t\t\t\t\t/\\.ts$/,\n\t\t\t\t\t\t'.handler',\n\t\t\t\t\t),\n\t\t\t\t\ttimeout: construct.timeout,\n\t\t\t\t\tmemorySize: construct.memorySize,\n\t\t\t\t\tenvironment: await construct.getEnvironment({\n\t\t\t\t\t\tmarkOptional: context.markOptional,\n\t\t\t\t\t}),\n\t\t\t\t\tdependencies: construct.constructs,\n\t\t\t\t\tauthorizer: construct.authorizer?.name ?? 'none',\n\t\t\t\t};\n\n\t\t\t\troutes.push(routeInfo);\n\t\t\t\tlogger.log(\n\t\t\t\t\t`Generated handler for ${routeInfo.method} ${routeInfo.path}`,\n\t\t\t\t);\n\t\t\t}\n\t\t} else {\n\t\t\t// Generate individual handler files for AWS API Gateway providers\n\t\t\tfor (const { key, construct, path } of constructs) {\n\t\t\t\tconst handlerFile = await this.generateHandlerFile(\n\t\t\t\t\toutputDir,\n\t\t\t\t\tpath.relative,\n\t\t\t\t\tkey,\n\t\t\t\t\tprovider,\n\t\t\t\t\tconstruct,\n\t\t\t\t\tcontext,\n\t\t\t\t);\n\n\t\t\t\tconst routeInfo: RouteInfo = {\n\t\t\t\t\tpath: construct._path,\n\t\t\t\t\tmethod: construct.method,\n\t\t\t\t\thandler: relative(process.cwd(), handlerFile).replace(\n\t\t\t\t\t\t/\\.ts$/,\n\t\t\t\t\t\t'.handler',\n\t\t\t\t\t),\n\t\t\t\t\ttimeout: construct.timeout,\n\t\t\t\t\tmemorySize: construct.memorySize,\n\t\t\t\t\tenvironment: await construct.getEnvironment({\n\t\t\t\t\t\tmarkOptional: context.markOptional,\n\t\t\t\t\t}),\n\t\t\t\t\tdependencies: construct.constructs,\n\t\t\t\t\tauthorizer: construct.authorizer?.name ?? 'none',\n\t\t\t\t};\n\n\t\t\t\troutes.push(routeInfo);\n\t\t\t\tlogger.log(\n\t\t\t\t\t`Generated handler for ${routeInfo.method} ${routeInfo.path}`,\n\t\t\t\t);\n\t\t\t}\n\t\t}\n\n\t\treturn routes;\n\t}\n\n\tprivate async generateHandlerFile(\n\t\toutputDir: string,\n\t\tsourceFile: string,\n\t\texportName: string,\n\t\tprovider: LegacyProvider,\n\t\t_endpoint: Endpoint<\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany,\n\t\t\tany\n\t\t>,\n\t\tcontext: BuildContext,\n\t): Promise<string> {\n\t\tconst handlerFileName = `${exportName}.ts`;\n\t\tconst handlerPath = join(outputDir, handlerFileName);\n\n\t\tconst relativePath = relative(dirname(handlerPath), sourceFile);\n\t\tconst importPath = relativePath.replace(/\\.ts$/, '.js');\n\n\t\tlet content: string;\n\n\t\tswitch (provider) {\n\t\t\tcase 'aws-apigatewayv1':\n\t\t\t\tcontent = this.generateAWSApiGatewayV1Handler(\n\t\t\t\t\timportPath,\n\t\t\t\t\texportName,\n\t\t\t\t\tcontext.storageDrivers,\n\t\t\t\t);\n\t\t\t\tbreak;\n\t\t\tcase 'aws-apigatewayv2':\n\t\t\t\tcontent = this.generateAWSApiGatewayV2Handler(\n\t\t\t\t\timportPath,\n\t\t\t\t\texportName,\n\t\t\t\t\tcontext.storageDrivers,\n\t\t\t\t);\n\t\t\t\tbreak;\n\t\t\tcase 'server':\n\t\t\t\tcontent = this.generateServerHandler(importPath, exportName);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new Error(`Unsupported provider: ${provider}`);\n\t\t}\n\n\t\tawait writeFile(handlerPath, content);\n\t\treturn handlerPath;\n\t}\n\n\tprivate async generateEndpointsFile(\n\t\toutputDir: string,\n\t\tendpoints: GeneratedConstruct<\n\t\t\tEndpoint<\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany\n\t\t\t>\n\t\t>[],\n\t\tcontext: BuildContext,\n\t): Promise<string> {\n\t\tconst endpointsFileName = 'endpoints.ts';\n\t\tconst endpointsPath = join(outputDir, endpointsFileName);\n\n\t\t// Group imports by file\n\t\tconst importsByFile = new Map<string, string[]>();\n\n\t\tfor (const { path, key } of endpoints) {\n\t\t\tconst relativePath = relative(dirname(endpointsPath), path.relative);\n\t\t\tconst importPath = relativePath.replace(/\\.ts$/, '.js');\n\n\t\t\tif (!importsByFile.has(importPath)) {\n\t\t\t\timportsByFile.set(importPath, []);\n\t\t\t}\n\t\t\timportsByFile.get(importPath)?.push(key);\n\t\t}\n\n\t\t// Generate import statements for endpoints\n\t\tconst endpointImports = Array.from(importsByFile.entries())\n\t\t\t.map(\n\t\t\t\t([importPath, exports]) =>\n\t\t\t\t\t`import { ${exports.join(', ')} } from '${importPath}';`,\n\t\t\t)\n\t\t\t.join('\\n');\n\n\t\tconst allExportNames = endpoints.map(({ key }) => key);\n\n\t\t// Check if we should use optimized handler generation\n\t\tif (context.production?.enabled && context.production.optimizedHandlers) {\n\t\t\treturn this.generateOptimizedEndpointsFile(\n\t\t\t\tendpointsPath,\n\t\t\t\tendpoints,\n\t\t\t\tendpointImports,\n\t\t\t\tallExportNames,\n\t\t\t);\n\t\t}\n\n\t\t// Standard generation (development or optimizedHandlers: false)\n\t\tconst content = `import type { EnvironmentParser } from '@geekmidas/envkit';\nimport type { Logger } from '@geekmidas/logger';\nimport { HonoEndpoint } from '@geekmidas/constructs/hono';\nimport { Endpoint } from '@geekmidas/constructs/endpoints';\nimport { ServiceDiscovery } from '@geekmidas/services';\nimport type { Hono } from 'hono';\n${endpointImports}\n\nexport const endpoints: Endpoint<any, any, any, any, any, any, any, any, any, any, any, any, any, any>[] = [\n ${allExportNames.join(',\\n ')}\n];\n\nexport async function setupEndpoints(\n app: Hono,\n envParser: EnvironmentParser<any>,\n logger: Logger,\n enableOpenApi: boolean = true,\n): Promise<void> {\n const serviceDiscovery = ServiceDiscovery.getInstance(envParser);\n\n // Configure OpenAPI options based on enableOpenApi flag\n const openApiOptions: any = enableOpenApi ? {\n docsPath: '/__docs',\n openApiOptions: {\n title: 'API Documentation',\n version: '1.0.0',\n description: 'Generated API documentation'\n }\n } : { docsPath: false };\n\n HonoEndpoint.addRoutes(endpoints, serviceDiscovery, app, openApiOptions);\n\n // Add Swagger UI if OpenAPI is enabled\n if (enableOpenApi) {\n try {\n const { swaggerUI } = await import('@hono/swagger-ui');\n app.get('/__docs/ui', swaggerUI({ url: '/__docs' }));\n } catch {\n // @hono/swagger-ui not installed, skip Swagger UI\n }\n }\n}\n`;\n\n\t\tawait writeFile(endpointsPath, content);\n\n\t\treturn endpointsPath;\n\t}\n\n\t/**\n\t * Generate optimized endpoints files with nested folder structure (per-endpoint files)\n\t */\n\tprivate async generateOptimizedEndpointsFile(\n\t\tendpointsPath: string,\n\t\tendpoints: GeneratedConstruct<\n\t\t\tEndpoint<\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany,\n\t\t\t\tany\n\t\t\t>\n\t\t>[],\n\t\t_endpointImports: string,\n\t\t_allExportNames: string[],\n\t): Promise<string> {\n\t\tconst logger = console;\n\t\tconst outputDir = dirname(endpointsPath);\n\n\t\t// Create endpoints subdirectory with tier folders\n\t\tconst endpointsDir = join(outputDir, 'endpoints');\n\t\tawait mkdir(join(endpointsDir, 'minimal'), { recursive: true });\n\t\tawait mkdir(join(endpointsDir, 'standard'), { recursive: true });\n\t\tawait mkdir(join(endpointsDir, 'full'), { recursive: true });\n\n\t\t// Analyze each endpoint\n\t\tconst analyses: EndpointAnalysis[] = endpoints.map(({ key, construct }) =>\n\t\t\tanalyzeEndpoint(construct, key),\n\t\t);\n\n\t\t// Build endpoint import info with correct relative paths from each tier folder\n\t\t// Use paths relative to the tier folder (e.g., endpoints/standard/)\n\t\tconst endpointImports: EndpointImportInfo[] = endpoints.map(\n\t\t\t({ key, path }) => {\n\t\t\t\t// Calculate relative path from tier folder (one level deeper than endpointsDir)\n\t\t\t\tconst tierDir = join(endpointsDir, 'standard'); // Use any tier as reference - same depth\n\t\t\t\tconst relativePath = relative(tierDir, path.relative);\n\t\t\t\tconst importPath = relativePath.replace(/\\.ts$/, '.js');\n\t\t\t\treturn { exportName: key, importPath };\n\t\t\t},\n\t\t);\n\n\t\t// Log analysis summary\n\t\tconst summary = summarizeAnalysis(analyses);\n\t\tlogger.log(`\\n📊 Endpoint Analysis:`);\n\t\tlogger.log(` Total: ${summary.total} endpoints`);\n\t\tlogger.log(\n\t\t\t` - Minimal (near-raw-Hono): ${summary.byTier.minimal} endpoints`,\n\t\t);\n\t\tlogger.log(\n\t\t\t` - Standard (auth/services): ${summary.byTier.standard} endpoints`,\n\t\t);\n\t\tlogger.log(\n\t\t\t` - Full (audits/rls/rate-limit): ${summary.byTier.full} endpoints`,\n\t\t);\n\n\t\t// Generate files with nested structure (per-endpoint files)\n\t\tconst files = generateEndpointFilesNested(analyses, endpointImports);\n\n\t\t// Write each file, creating directories as needed\n\t\tfor (const [filename, content] of Object.entries(files)) {\n\t\t\tconst filePath = join(endpointsDir, filename);\n\t\t\tawait mkdir(dirname(filePath), { recursive: true });\n\t\t\tawait writeFile(filePath, content);\n\t\t}\n\n\t\t// Count files by type\n\t\tconst endpointFiles = Object.keys(files).filter(\n\t\t\t(f) => !f.endsWith('index.ts') && !f.endsWith('validators.ts'),\n\t\t).length;\n\t\tconst indexFiles = Object.keys(files).filter((f) =>\n\t\t\tf.endsWith('index.ts'),\n\t\t).length;\n\n\t\tlogger.log(\n\t\t\t` Generated ${endpointFiles} endpoint files + ${indexFiles} index files + validators.ts`,\n\t\t);\n\n\t\t// Return path to index file\n\t\treturn join(endpointsDir, 'index.ts');\n\t}\n\n\tprivate async generateAppFile(\n\t\toutputDir: string,\n\t\tcontext: BuildContext,\n\t): Promise<string> {\n\t\t// Use production generator if in production mode\n\t\tif (context.production?.enabled) {\n\t\t\treturn this.generateProductionAppFile(outputDir, context);\n\t\t}\n\n\t\tconst appFileName = 'app.ts';\n\t\tconst appPath = join(outputDir, appFileName);\n\n\t\t// The logger and the env parser, from the surface that already holds them.\n\t\tconst runtime = runtimeFor(context, dirname(appPath));\n\n\t\t// Generate telescope imports and setup if enabled\n\t\tconst telescopeEnabled = context.telescope?.enabled;\n\t\tconst telescopeWebSocketEnabled = context.telescope?.websocket;\n\t\tconst usesExternalTelescope = !!context.telescope?.telescopePath;\n\n\t\t// Generate studio imports and setup if enabled\n\t\tconst studioEnabled = context.studio?.enabled;\n\t\tconst usesExternalStudio = !!context.studio?.studioPath;\n\t\t// Studio from the declared database rather than from a module someone\n\t\t// wrote to resolve one. Every input it takes is derivable: the client\n\t\t// from the construct, the rest defaults.\n\t\tconst studioFromDatabase =\n\t\t\t!usesExternalStudio && !!context.studio?.database;\n\n\t\t// Generate imports based on whether telescope is external or inline\n\t\tconst telescopeFromSurface =\n\t\t\t!!context.surface?.module && !usesExternalTelescope;\n\n\t\tlet telescopeImports = '';\n\t\tif (telescopeEnabled) {\n\t\t\tif (telescopeFromSurface) {\n\t\t\t\t// The surface was declared with a Telescope, and the entry already\n\t\t\t\t// imports the surface. Nothing to print but the middleware.\n\t\t\t\ttelescopeImports =\n\t\t\t\t\t\"import { createMiddleware, createUI } from '@geekmidas/telescope/hono';\";\n\t\t\t} else if (usesExternalTelescope) {\n\t\t\t\tconst relativeTelescopePath = relative(\n\t\t\t\t\tdirname(appPath),\n\t\t\t\t\tcontext.telescope?.telescopePath!,\n\t\t\t\t);\n\t\t\t\ttelescopeImports = `import ${context.telescope?.telescopeImportPattern} from '${relativeTelescopePath}';\nimport { createMiddleware, createUI } from '@geekmidas/telescope/hono';`;\n\t\t\t} else {\n\t\t\t\ttelescopeImports = `import { Telescope, InMemoryStorage } from '@geekmidas/telescope';\nimport { createMiddleware, createUI } from '@geekmidas/telescope/hono';`;\n\t\t\t}\n\t\t}\n\n\t\t// Generate imports for studio\n\t\tlet studioImports = '';\n\t\tif (studioEnabled) {\n\t\t\tif (usesExternalStudio) {\n\t\t\t\tconst relativeStudioPath = relative(\n\t\t\t\t\tdirname(appPath),\n\t\t\t\t\tcontext.studio?.studioPath!,\n\t\t\t\t);\n\t\t\t\tstudioImports = `import ${context.studio?.studioImportPattern} from '${relativeStudioPath}';\nimport { createStudioApp } from '@geekmidas/studio/server/hono';`;\n\t\t\t} else if (studioFromDatabase) {\n\t\t\t\tconst dbSpecifier = importSpecifier(\n\t\t\t\t\tdirname(appPath),\n\t\t\t\t\tcontext.studio!.database!.specifier,\n\t\t\t\t);\n\t\t\t\tstudioImports = `import { snifferContext } from '@geekmidas/constructs';\nimport { Direction, InMemoryMonitoringStorage, Studio } from '@geekmidas/studio';\nimport { ${context.studio!.database!.exportName} as __studioDb } from '${dbSpecifier}';\nimport { createStudioApp } from '@geekmidas/studio/server/hono';`;\n\t\t\t} else {\n\t\t\t\tstudioImports = '';\n\t\t\t}\n\t\t}\n\n\t\t// Generate imports for server hooks\n\t\tconst cors = corsFor(context.surface);\n\t\tlet hooksImports = '';\n\t\tlet beforeSetupCall = '';\n\t\tlet afterSetupCall = '';\n\t\tif (context.hooks?.serverHooksPath) {\n\t\t\tconst relativeHooksPath = relative(\n\t\t\t\tdirname(appPath),\n\t\t\t\tcontext.hooks.serverHooksPath,\n\t\t\t);\n\t\t\thooksImports = `import * as serverHooks from '${relativeHooksPath}';`;\n\t\t\tbeforeSetupCall = `\n // Call beforeSetup hook if defined\n if (typeof serverHooks.beforeSetup === 'function') {\n await serverHooks.beforeSetup(honoApp, { envParser, logger });\n }\n`;\n\t\t\tafterSetupCall = `\n // Call afterSetup hook if defined\n if (typeof serverHooks.afterSetup === 'function') {\n await serverHooks.afterSetup(honoApp, { envParser, logger });\n }\n`;\n\t\t}\n\n\t\tconst telescopeWebSocketSetupCode = telescopeWebSocketEnabled\n\t\t\t? `\n // Setup WebSocket for real-time telescope updates\n try {\n const { createNodeWebSocket } = await import('@hono/node-ws');\n const { injectWebSocket, upgradeWebSocket } = createNodeWebSocket({ app: honoApp });\n // Add WebSocket route directly to main app (sub-app routes don't support WS upgrade)\n honoApp.get('${context.telescope?.path}/ws', upgradeWebSocket(() => ({\n onOpen: (_event: Event, ws: any) => {\n telescope.addWsClient(ws);\n },\n onClose: (_event: Event, ws: any) => {\n telescope.removeWsClient(ws);\n },\n onMessage: (event: MessageEvent, ws: any) => {\n try {\n const data = JSON.parse(event.data);\n if (data.type === 'ping') {\n ws.send(JSON.stringify({ type: 'pong' }));\n }\n } catch {\n // Ignore invalid messages\n }\n },\n })));\n // Store injectWebSocket for server entry to call after serve()\n (honoApp as any).__injectWebSocket = injectWebSocket;\n logger.info('Telescope WebSocket enabled');\n } catch (e) {\n logger.warn({ error: e }, 'WebSocket support not available - install @hono/node-ws for real-time updates');\n }\n`\n\t\t\t: '';\n\n\t\t// Generate telescope setup - either use external instance or create inline\n\t\tlet telescopeSetup = '';\n\t\tif (telescopeEnabled) {\n\t\t\tif (telescopeFromSurface || usesExternalTelescope) {\n\t\t\t\t// Use external telescope instance - no need to create one\n\t\t\t\ttelescopeSetup = `\n${telescopeWebSocketSetupCode}\n // Add telescope middleware (before endpoints to capture all requests)\n honoApp.use('*', createMiddleware(telescope));\n\n // Mount telescope UI\n const telescopeUI = createUI(telescope);\n honoApp.route('${context.telescope?.path}', telescopeUI);\n`;\n\t\t\t} else {\n\t\t\t\t// Create inline telescope instance\n\t\t\t\ttelescopeSetup = `\n // Setup Telescope for debugging/monitoring\n const telescopeStorage = new InMemoryStorage({ maxEntries: ${context.telescope?.maxEntries} });\n const telescope = new Telescope({\n enabled: true,\n path: '${context.telescope?.path}',\n ignorePatterns: ${JSON.stringify(context.telescope?.ignore)},\n recordBody: ${context.telescope?.recordBody},\n storage: telescopeStorage,\n });\n${telescopeWebSocketSetupCode}\n // Add telescope middleware (before endpoints to capture all requests)\n honoApp.use('*', createMiddleware(telescope));\n\n // Mount telescope UI\n const telescopeUI = createUI(telescope);\n honoApp.route('${context.telescope?.path}', telescopeUI);\n`;\n\t\t\t}\n\t\t}\n\n\t\t// Generate studio setup - requires external instance\n\t\tlet studioSetup = '';\n\t\tif (studioEnabled && studioFromDatabase) {\n\t\t\tstudioSetup = `\n // Studio, built from the declared database. The client comes from the\n // construct, so what you inspect is by definition what the handlers write to.\n const studio = new Studio({\n monitoring: { storage: new InMemoryMonitoringStorage({ maxEntries: 100 }) },\n data: {\n db: await __studioDb.service.register({ envParser, context: snifferContext }),\n cursor: { field: 'id', direction: Direction.Desc },\n },\n enabled: true,\n });\n\n const studioApp = createStudioApp(studio);\n honoApp.route('${context.studio?.path}', studioApp);\n`;\n\t\t} else if (studioEnabled && usesExternalStudio) {\n\t\t\tstudioSetup = `\n // Mount Studio data browser UI\n const studioApp = createStudioApp(studio);\n honoApp.route('${context.studio?.path}', studioApp);\n`;\n\t\t}\n\n\t\tconst content = `/**\n * Generated server application\n *\n * ⚠️ WARNING: This is for LOCAL DEVELOPMENT ONLY\n * The subscriber polling mechanism is not production-ready.\n * For production, use AWS Lambda with SQS/SNS event sources.\n */\nimport { Hono } from 'hono';\nimport type { Hono as HonoType } from 'hono';\nimport { setupEndpoints } from './endpoints.js';\nimport { setupSubscribers } from './subscribers.js';\nimport { setupQueues } from './queues.js';\n${runtime.imports}\n${telescopeImports}\n${studioImports}\n${hooksImports}\n${cors.imports}\n${context.storageDrivers?.imports ?? ''}\n\n${runtime.bindings}\n${telescopeFromSurface ? 'const telescope = __surface.telescope;' : ''}\n\n${\n\tcontext.storageDrivers?.setup\n\t\t? `// Which storage drivers exist is the entry point's decision: the scheme in\n// each injected URL picks one, so no construct and no application module names\n// a provider.\n${context.storageDrivers.setup}\n`\n\t\t: ''\n}\nexport interface ServerApp {\n app: HonoType;\n start: (options?: {\n port?: number;\n serve: (app: HonoType, port: number) => void | Promise<void>;\n }) => Promise<void>;\n}\n\n/**\n * Create and configure the Hono application\n *\n * @param app - Optional Hono app instance to configure (creates new one if not provided)\n * @param enableOpenApi - Enable OpenAPI documentation (default: true)\n * @returns Server app with configured Hono app and start function\n *\n * @example\n * // With Bun\n * import { createApp } from './.gkm/server/app.js';\n *\n * const { app, start } = await createApp();\n *\n * await start({\n * port: 3000,\n * serve: (app, port) => {\n * Bun.serve({ port, fetch: app.fetch });\n * }\n * });\n *\n * @example\n * // With Node.js (using @hono/node-server)\n * import { serve } from '@hono/node-server';\n * import { createApp } from './.gkm/server/app.js';\n *\n * const { app, start } = await createApp();\n *\n * await start({\n * port: 3000,\n * serve: (app, port) => {\n * serve({ fetch: app.fetch, port });\n * }\n * });\n */\nexport async function createApp(app?: HonoType, enableOpenApi: boolean = true): Promise<ServerApp> {\n const honoApp = app || new Hono();\n${telescopeSetup}${cors.setup}${beforeSetupCall}${studioSetup}\n // Setup HTTP endpoints\n await setupEndpoints(honoApp, envParser, logger, enableOpenApi);\n${afterSetupCall}\n\n return {\n app: honoApp,\n async start(options) {\n if (!options?.serve) {\n throw new Error(\n 'serve function is required. Pass a serve function for your runtime:\\\\n' +\n ' - Bun: (app, port) => Bun.serve({ port, fetch: app.fetch })\\\\n' +\n ' - Node: (app, port) => serve({ fetch: app.fetch, port })'\n );\n }\n\n const port = options.port ?? 3000;\n\n // Start subscribers in background (non-blocking, local development only)\n await setupSubscribers(envParser, logger).catch((error) => {\n logger.error({ error }, 'Failed to start subscribers');\n });\n\n // Start queue workers in background (non-blocking, local development only)\n await setupQueues(envParser, logger).catch((error) => {\n logger.error({ error }, 'Failed to start queue workers');\n });\n\n logger.info({ port }, 'Starting server');\n\n // Start HTTP server using provided serve function\n await options.serve(honoApp, port);\n\n logger.info({ port }, 'Server started');\n }\n };\n}\n\n// Default export for convenience\nexport default createApp;\n`;\n\n\t\tawait writeFile(appPath, content);\n\n\t\treturn appPath;\n\t}\n\n\t/**\n\t * One Lambda, one endpoint — and no environment import.\n\t *\n\t * The endpoint was built from its surface, so it carries the parser the\n\t * adaptor needs. This used to read\n\t * `import { envParser } from '../../config/env'`, a line the build wrote\n\t * because a generator can print a module specifier and cannot print an\n\t * object. Nothing has to be printed now, which is also why nothing has to be\n\t * named in config.\n\t */\n\tprivate generateAWSApiGatewayV1Handler(\n\t\timportPath: string,\n\t\texportName: string,\n\t\tdrivers?: StorageDrivers,\n\t): string {\n\t\treturn `import { AmazonApiGatewayV1Endpoint } from '@geekmidas/constructs/aws';\nimport { ${exportName} } from '${importPath}';\n${drivers?.imports ?? ''}\n${drivers?.setup ? `\\n// The handler registers the drivers its target needs.\\n${drivers.setup}\\n` : ''}\nconst adapter = new AmazonApiGatewayV1Endpoint(${exportName});\n\nexport const handler = adapter.handler;\n`;\n\t}\n\n\t/**\n\t * One Lambda, one endpoint — and no environment import.\n\t *\n\t * The endpoint was built from its surface, so it carries the parser the\n\t * adaptor needs. This used to read\n\t * `import { envParser } from '../../config/env'`, a line the build wrote\n\t * because a generator can print a module specifier and cannot print an\n\t * object. Nothing has to be printed now, which is also why nothing has to be\n\t * named in config.\n\t */\n\tprivate generateAWSApiGatewayV2Handler(\n\t\timportPath: string,\n\t\texportName: string,\n\t\tdrivers?: StorageDrivers,\n\t): string {\n\t\treturn `import { AmazonApiGatewayV2Endpoint } from '@geekmidas/constructs/aws';\nimport { ${exportName} } from '${importPath}';\n${drivers?.imports ?? ''}\n${drivers?.setup ? `\\n// The handler registers the drivers its target needs.\\n${drivers.setup}\\n` : ''}\nconst adapter = new AmazonApiGatewayV2Endpoint(${exportName});\n\nexport const handler = adapter.handler;\n`;\n\t}\n\n\tprivate generateServerHandler(\n\t\timportPath: string,\n\t\texportName: string,\n\t): string {\n\t\treturn `import { ${exportName} } from '${importPath}';\n\n// Server handler - implement based on your server framework\nexport const handler = ${exportName};\n`;\n\t}\n\n\t/**\n\t * Generate a production-optimized app.ts file\n\t * No dev tools (Telescope, Studio, WebSocket), includes health checks and graceful shutdown\n\t */\n\tprivate async generateProductionAppFile(\n\t\toutputDir: string,\n\t\tcontext: BuildContext,\n\t): Promise<string> {\n\t\tconst appFileName = 'app.ts';\n\t\tconst appPath = join(outputDir, appFileName);\n\n\t\tconst relativeLoggerPath = relative(dirname(appPath), context.loggerPath);\n\t\tconst relativeEnvParserPath = relative(\n\t\t\tdirname(appPath),\n\t\t\tcontext.envParserPath,\n\t\t);\n\n\t\tconst production = context.production!;\n\t\tconst healthCheckPath = production.healthCheck;\n\t\tconst enableGracefulShutdown = production.gracefulShutdown;\n\t\tconst enableOpenApi = production.openapi;\n\t\tconst includeSubscribers = production.subscribers === 'include';\n\n\t\t// Generate imports for server hooks\n\t\tconst cors = corsFor(context.surface);\n\t\tlet hooksImports = '';\n\t\tlet beforeSetupCall = '';\n\t\tlet afterSetupCall = '';\n\t\tif (context.hooks?.serverHooksPath) {\n\t\t\tconst relativeHooksPath = relative(\n\t\t\t\tdirname(appPath),\n\t\t\t\tcontext.hooks.serverHooksPath,\n\t\t\t);\n\t\t\thooksImports = `import * as serverHooks from '${relativeHooksPath}';`;\n\t\t\tbeforeSetupCall = `\n // Call beforeSetup hook if defined\n if (typeof serverHooks.beforeSetup === 'function') {\n await serverHooks.beforeSetup(honoApp, { envParser, logger });\n }\n`;\n\t\t\tafterSetupCall = `\n // Call afterSetup hook if defined\n if (typeof serverHooks.afterSetup === 'function') {\n await serverHooks.afterSetup(honoApp, { envParser, logger });\n }\n`;\n\t\t}\n\n\t\t// Subscriber + queue setup code (background workers share the same flag)\n\t\tconst subscriberSetup = includeSubscribers\n\t\t\t? `\n // Start subscribers in background\n await setupSubscribers(envParser, logger).catch((error) => {\n logger.error({ error }, 'Failed to start subscribers');\n });\n\n // Start queue workers in background\n await setupQueues(envParser, logger).catch((error) => {\n logger.error({ error }, 'Failed to start queue workers');\n });\n`\n\t\t\t: '';\n\n\t\tconst subscriberImport = includeSubscribers\n\t\t\t? `import { setupSubscribers } from './subscribers.js';\nimport { setupQueues } from './queues.js';`\n\t\t\t: '';\n\n\t\t// Graceful shutdown code\n\t\tconst gracefulShutdownCode = enableGracefulShutdown\n\t\t\t? `\n // Graceful shutdown handling\n let isShuttingDown = false;\n\n const shutdown = async () => {\n if (isShuttingDown) return;\n isShuttingDown = true;\n logger.info('Graceful shutdown initiated');\n // Allow in-flight requests to complete (30s timeout)\n setTimeout(() => process.exit(0), 30000);\n };\n\n process.on('SIGTERM', shutdown);\n process.on('SIGINT', shutdown);\n`\n\t\t\t: '';\n\n\t\t// Use endpoints/index.js for optimized builds, endpoints.js otherwise\n\t\tconst endpointsImportPath = production.optimizedHandlers\n\t\t\t? './endpoints/index.js'\n\t\t\t: './endpoints.js';\n\n\t\tconst content = `/**\n * Generated production server application\n *\n * This is a production-optimized build without dev tools.\n * - No Telescope debugging dashboard\n * - No Studio database browser\n * - No WebSocket updates\n * - Includes health checks and graceful shutdown\n */\nimport { Hono } from 'hono';\nimport type { Hono as HonoType } from 'hono';\nimport { setupEndpoints } from '${endpointsImportPath}';\n${subscriberImport}\nimport ${context.envParserImportPattern} from '${relativeEnvParserPath}';\nimport ${context.loggerImportPattern} from '${relativeLoggerPath}';\n${hooksImports}\n${cors.imports}\n${context.storageDrivers?.imports ?? ''}\n\n${\n\tcontext.storageDrivers?.setup\n\t\t? `// The entry point registers the drivers its target needs.\n${context.storageDrivers.setup}\n`\n\t\t: ''\n}\nexport interface ServerApp {\n app: HonoType;\n start: (options?: {\n port?: number;\n serve: (app: HonoType, port: number) => void | Promise<void>;\n }) => Promise<void>;\n}\n\n/**\n * Create and configure the production Hono application\n */\nexport async function createApp(app?: HonoType): Promise<ServerApp> {\n const honoApp = app || new Hono();\n\n // Health check endpoint (always first)\n honoApp.get('${healthCheckPath}', (c) => c.json({ status: 'ok', timestamp: Date.now() }));\n honoApp.get('/ready', (c) => c.json({ ready: true }));\n${cors.setup}${beforeSetupCall}\n // Setup HTTP endpoints (OpenAPI: ${enableOpenApi})\n await setupEndpoints(honoApp, envParser, logger, ${enableOpenApi});\n${afterSetupCall}\n return {\n app: honoApp,\n async start(options) {\n if (!options?.serve) {\n throw new Error(\n 'serve function is required. Pass a serve function for your runtime:\\\\n' +\n ' - Bun: (app, port) => Bun.serve({ port, fetch: app.fetch })\\\\n' +\n ' - Node: (app, port) => serve({ fetch: app.fetch, port })'\n );\n }\n\n const port = options.port ?? Number(process.env.PORT) ?? 3000;\n${gracefulShutdownCode}${subscriberSetup}\n logger.info({ port }, 'Starting production server');\n\n // Start HTTP server using provided serve function\n await options.serve(honoApp, port);\n\n logger.info({ port }, 'Production server started');\n }\n };\n}\n\n// Default export for convenience\nexport default createApp;\n`;\n\n\t\tawait writeFile(appPath, content);\n\n\t\t// Also generate the production server entry point\n\t\tawait this.generateProductionServerEntry(outputDir);\n\n\t\treturn appPath;\n\t}\n\n\t/**\n\t * Generate production server.ts entry point\n\t */\n\tprivate async generateProductionServerEntry(\n\t\toutputDir: string,\n\t): Promise<void> {\n\t\tconst serverPath = join(outputDir, 'server.ts');\n\n\t\tconst content = `#!/usr/bin/env node\n/**\n * Production server entry point\n * Generated by 'gkm build --provider server --production'\n */\nimport { serve } from '@hono/node-server';\nimport { createApp } from './app.js';\n\nconst port = Number(process.env.PORT) || 3000;\n\nconst { start } = await createApp();\n\nawait start({\n port,\n serve: (app, port) => { serve({ fetch: app.fetch, port }); },\n});\n`;\n\n\t\tawait writeFile(serverPath, content);\n\t}\n}\n","import type { Endpoint } from '@geekmidas/constructs/endpoints';\nimport {\n\tgetRegisteredZodJsonSchemas,\n\tgetSchemaMetadata,\n\tStandardSchemaJsonSchema,\n} from '@geekmidas/schema/conversion';\nimport type { StandardSchemaV1 } from '@standard-schema/spec';\n\ninterface OpenApiTsOptions {\n\ttitle?: string;\n\tversion?: string;\n\tdescription?: string;\n}\n\n// JSON Schema type definition\ninterface JsonSchema {\n\ttype?: string;\n\tproperties?: Record<string, JsonSchema>;\n\titems?: JsonSchema;\n\trequired?: string[];\n\tenum?: string[];\n\t$ref?: string;\n\tanyOf?: JsonSchema[];\n\toneOf?: JsonSchema[];\n\tallOf?: JsonSchema[];\n\tadditionalProperties?: boolean | JsonSchema;\n\t[key: string]: unknown;\n}\n\n// Security scheme type (OpenAPI 3.1)\ninterface SecuritySchemeObject {\n\ttype: 'apiKey' | 'http' | 'mutualTLS' | 'oauth2' | 'openIdConnect';\n\tdescription?: string;\n\tname?: string;\n\tin?: 'query' | 'header' | 'cookie';\n\tscheme?: string;\n\tbearerFormat?: string;\n\tflows?: Record<string, unknown>;\n\topenIdConnectUrl?: string;\n\t[key: string]: unknown;\n}\n\ninterface EndpointInfo {\n\tendpoint: string;\n\troute: string;\n\tmethod: string;\n\tauthorizerName: string | null;\n\t/** @deprecated Use securityScheme instead */\n\tauthorizerType: string | null;\n\t/** The OpenAPI security scheme definition for this endpoint's authorizer */\n\tsecurityScheme: SecuritySchemeObject | null;\n\tinput?: {\n\t\tbody?: StandardSchemaV1;\n\t\tquery?: StandardSchemaV1;\n\t\tparams?: StandardSchemaV1;\n\t};\n\toutput?: StandardSchemaV1;\n\tdescription?: string;\n\ttags?: string[];\n\toperationId?: string;\n\tresponseType: string;\n}\n\ninterface SecuritySchemeInfo {\n\tname: string;\n\ttype: string;\n\tscheme: SecuritySchemeObject;\n}\n\n/**\n * Generates TypeScript OpenAPI module from endpoints.\n * Outputs:\n * - securitySchemes: typed security scheme definitions\n * - endpointAuth: runtime map of endpoints to auth requirements\n * - paths: TypeScript interface for type-safe fetcher\n * - schema interfaces: reusable TypeScript types from Zod/Valibot schemas\n */\nexport class OpenApiTsGenerator {\n\tasync generate(\n\t\tendpoints: Endpoint<any, any, any, any, any, any>[],\n\t\toptions: OpenApiTsOptions = {},\n\t): Promise<string> {\n\t\tconst { title = 'API', version = '1.0.0', description } = options;\n\n\t\t// Extract endpoint info\n\t\tconst endpointInfos = await this.extractEndpointInfos(endpoints);\n\n\t\t// Collect unique security schemes\n\t\tconst securitySchemes = this.collectSecuritySchemes(endpointInfos);\n\n\t\t// Build endpoint auth map\n\t\tconst endpointAuth = this.buildEndpointAuthMap(endpointInfos);\n\n\t\t// Generate schema interfaces\n\t\tconst schemaInterfaces = await this.generateSchemaInterfaces(endpointInfos);\n\n\t\t// Generate paths interface\n\t\tconst pathsInterface = await this.generatePathsInterface(endpointInfos);\n\n\t\t// Build the final TypeScript module\n\t\treturn this.buildModule({\n\t\t\ttitle,\n\t\t\tversion,\n\t\t\tdescription,\n\t\t\tsecuritySchemes,\n\t\t\tendpointAuth,\n\t\t\tschemaInterfaces,\n\t\t\tpathsInterface,\n\t\t});\n\t}\n\n\tprivate async extractEndpointInfos(\n\t\tendpoints: Endpoint<any, any, any, any, any, any>[],\n\t): Promise<EndpointInfo[]> {\n\t\treturn endpoints.map((ep) => {\n\t\t\tconst route = ep.route.replace(/:(\\w+)/g, '{$1}');\n\t\t\tconst method = ep.method.toUpperCase();\n\n\t\t\t// Get security scheme from authorizer (if available)\n\t\t\t// This is the preferred way - the scheme is stored directly on the authorizer\n\t\t\tconst securityScheme = ep.authorizer?.securityScheme as\n\t\t\t\t| SecuritySchemeObject\n\t\t\t\t| undefined;\n\n\t\t\treturn {\n\t\t\t\tendpoint: `${method} ${route}`,\n\t\t\t\troute,\n\t\t\t\tmethod,\n\t\t\t\tauthorizerName: ep.authorizer?.name ?? null,\n\t\t\t\tauthorizerType: ep.authorizer?.type ?? null,\n\t\t\t\tsecurityScheme: securityScheme ?? null,\n\t\t\t\tinput: ep.input,\n\t\t\t\toutput: ep.outputSchema,\n\t\t\t\tdescription: ep.description,\n\t\t\t\ttags: ep.tags,\n\t\t\t\toperationId: ep.operationId,\n\t\t\t\tresponseType: ep.responseType ?? 'application/json',\n\t\t\t};\n\t\t});\n\t}\n\n\tprivate collectSecuritySchemes(\n\t\tendpointInfos: EndpointInfo[],\n\t): SecuritySchemeInfo[] {\n\t\tconst schemes = new Map<string, SecuritySchemeInfo>();\n\n\t\tfor (const info of endpointInfos) {\n\t\t\tif (info.authorizerName && !schemes.has(info.authorizerName)) {\n\t\t\t\t// Prefer the stored security scheme (from .securitySchemes() or built-ins)\n\t\t\t\t// Fall back to inference from authorizerType for backward compatibility\n\t\t\t\tconst scheme =\n\t\t\t\t\tinfo.securityScheme ??\n\t\t\t\t\t(info.authorizerType\n\t\t\t\t\t\t? this.mapAuthorizerToSecurityScheme(\n\t\t\t\t\t\t\t\tinfo.authorizerType,\n\t\t\t\t\t\t\t\tinfo.authorizerName,\n\t\t\t\t\t\t\t)\n\t\t\t\t\t\t: null);\n\n\t\t\t\tif (scheme) {\n\t\t\t\t\tschemes.set(info.authorizerName, {\n\t\t\t\t\t\tname: info.authorizerName,\n\t\t\t\t\t\ttype: scheme.type,\n\t\t\t\t\t\tscheme,\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn Array.from(schemes.values());\n\t}\n\n\tprivate mapAuthorizerToSecurityScheme(\n\t\ttype: string,\n\t\t_name: string,\n\t): SecuritySchemeObject {\n\t\tswitch (type.toLowerCase()) {\n\t\t\tcase 'jwt':\n\t\t\tcase 'bearer':\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'http',\n\t\t\t\t\tscheme: 'bearer',\n\t\t\t\t\tbearerFormat: 'JWT',\n\t\t\t\t};\n\t\t\tcase 'iam':\n\t\t\tcase 'aws-sigv4':\n\t\t\tcase 'sigv4':\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'apiKey',\n\t\t\t\t\tin: 'header',\n\t\t\t\t\tname: 'Authorization',\n\t\t\t\t\t'x-amazon-apigateway-authtype': 'awsSigv4',\n\t\t\t\t};\n\t\t\tcase 'apikey':\n\t\t\tcase 'api-key':\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'apiKey',\n\t\t\t\t\tin: 'header',\n\t\t\t\t\tname: 'X-API-Key',\n\t\t\t\t};\n\t\t\tcase 'oauth2':\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'oauth2',\n\t\t\t\t\tflows: {},\n\t\t\t\t};\n\t\t\tcase 'oidc':\n\t\t\tcase 'openidconnect':\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'openIdConnect',\n\t\t\t\t\topenIdConnectUrl: '',\n\t\t\t\t};\n\t\t\tdefault:\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'http',\n\t\t\t\t\tscheme: 'bearer',\n\t\t\t\t};\n\t\t}\n\t}\n\n\tprivate buildEndpointAuthMap(\n\t\tendpointInfos: EndpointInfo[],\n\t): Record<string, string | null> {\n\t\tconst authMap: Record<string, string | null> = {};\n\n\t\tfor (const info of endpointInfos) {\n\t\t\tauthMap[info.endpoint] = info.authorizerName;\n\t\t}\n\n\t\treturn authMap;\n\t}\n\n\tprivate async generateSchemaInterfaces(\n\t\tendpointInfos: EndpointInfo[],\n\t): Promise<string> {\n\t\tconst interfaces: string[] = [];\n\t\tconst generatedNames = new Set<string>();\n\t\t// Collect nested schemas with $defs (from .meta({ id: 'X' }))\n\t\tconst collectedDefs = new Map<string, JsonSchema>();\n\n\t\tfor (const info of endpointInfos) {\n\t\t\tconst baseName = this.getSchemaBaseName(info);\n\n\t\t\t// Input body schema\n\t\t\tif (info.input?.body) {\n\t\t\t\tconst name = await this.getSchemaName(\n\t\t\t\t\tinfo.input.body,\n\t\t\t\t\t`${baseName}Input`,\n\t\t\t\t);\n\t\t\t\tif (!generatedNames.has(name)) {\n\t\t\t\t\tconst schema = await this.schemaToInterfaceWithDefs(\n\t\t\t\t\t\tinfo.input.body,\n\t\t\t\t\t\tname,\n\t\t\t\t\t\tcollectedDefs,\n\t\t\t\t\t);\n\t\t\t\t\tif (schema) {\n\t\t\t\t\t\tinterfaces.push(schema);\n\t\t\t\t\t\tgeneratedNames.add(name);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Input params schema\n\t\t\tif (info.input?.params) {\n\t\t\t\tconst name = await this.getSchemaName(\n\t\t\t\t\tinfo.input.params,\n\t\t\t\t\t`${baseName}Params`,\n\t\t\t\t);\n\t\t\t\tif (!generatedNames.has(name)) {\n\t\t\t\t\tconst schema = await this.schemaToInterfaceWithDefs(\n\t\t\t\t\t\tinfo.input.params,\n\t\t\t\t\t\tname,\n\t\t\t\t\t\tcollectedDefs,\n\t\t\t\t\t);\n\t\t\t\t\tif (schema) {\n\t\t\t\t\t\tinterfaces.push(schema);\n\t\t\t\t\t\tgeneratedNames.add(name);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Input query schema\n\t\t\tif (info.input?.query) {\n\t\t\t\tconst name = await this.getSchemaName(\n\t\t\t\t\tinfo.input.query,\n\t\t\t\t\t`${baseName}Query`,\n\t\t\t\t);\n\t\t\t\tif (!generatedNames.has(name)) {\n\t\t\t\t\tconst schema = await this.schemaToInterfaceWithDefs(\n\t\t\t\t\t\tinfo.input.query,\n\t\t\t\t\t\tname,\n\t\t\t\t\t\tcollectedDefs,\n\t\t\t\t\t);\n\t\t\t\t\tif (schema) {\n\t\t\t\t\t\tinterfaces.push(schema);\n\t\t\t\t\t\tgeneratedNames.add(name);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Output schema\n\t\t\tif (info.output) {\n\t\t\t\tconst name = await this.getSchemaName(info.output, `${baseName}Output`);\n\t\t\t\tif (!generatedNames.has(name)) {\n\t\t\t\t\tconst schema = await this.schemaToInterfaceWithDefs(\n\t\t\t\t\t\tinfo.output,\n\t\t\t\t\t\tname,\n\t\t\t\t\t\tcollectedDefs,\n\t\t\t\t\t);\n\t\t\t\t\tif (schema) {\n\t\t\t\t\t\tinterfaces.push(schema);\n\t\t\t\t\t\tgeneratedNames.add(name);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Pull in every schema registered via `.meta({ id })` in zod's global\n\t\t// registry, even when no endpoint references it directly. This makes\n\t\t// derived schemas like `UserSchema.pick(...)` discoverable through the\n\t\t// named parent type without requiring the parent to be wired into an\n\t\t// endpoint.\n\t\tconst registrySchemas = await getRegisteredZodJsonSchemas();\n\t\tfor (const [rawName, rawSchema] of Object.entries(registrySchemas)) {\n\t\t\tconst defName = this.pascalCase(rawName);\n\t\t\tif (collectedDefs.has(defName) || generatedNames.has(defName)) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tconst {\n\t\t\t\tid: _id,\n\t\t\t\t$defs: _defs,\n\t\t\t\t...rest\n\t\t\t} = rawSchema as JsonSchema & {\n\t\t\t\tid?: string;\n\t\t\t};\n\t\t\tcollectedDefs.set(defName, rest as JsonSchema);\n\t\t}\n\n\t\t// Generate interfaces for collected $defs (nested schemas with .meta({ id: 'X' }))\n\t\tfor (const [defName, defSchema] of collectedDefs) {\n\t\t\tif (!generatedNames.has(defName)) {\n\t\t\t\tconst interfaceStr = this.jsonSchemaToInterface(defSchema, defName);\n\t\t\t\tinterfaces.push(interfaceStr);\n\t\t\t\tgeneratedNames.add(defName);\n\t\t\t}\n\t\t}\n\n\t\treturn interfaces.join('\\n\\n');\n\t}\n\n\t/**\n\t * Get the name for a schema, using metadata `id` if available,\n\t * otherwise falling back to the provided default name.\n\t */\n\tprivate async getSchemaName(\n\t\tschema: StandardSchemaV1,\n\t\tdefaultName: string,\n\t): Promise<string> {\n\t\ttry {\n\t\t\tconst metadata = await getSchemaMetadata(schema);\n\t\t\tif (metadata?.id) {\n\t\t\t\treturn this.pascalCase(metadata.id);\n\t\t\t}\n\t\t} catch {\n\t\t\t// Ignore metadata extraction errors\n\t\t}\n\t\treturn defaultName;\n\t}\n\n\tprivate getSchemaBaseName(info: EndpointInfo): string {\n\t\tif (info.operationId) {\n\t\t\treturn this.pascalCase(info.operationId);\n\t\t}\n\n\t\t// Generate name from method + route\n\t\tconst routeParts = info.route\n\t\t\t.replace(/[{}]/g, '')\n\t\t\t.split('/')\n\t\t\t.filter(Boolean)\n\t\t\t.map((part) => this.pascalCase(part));\n\n\t\treturn `${this.pascalCase(info.method.toLowerCase())}${routeParts.join('')}`;\n\t}\n\n\tprivate pascalCase(str: string): string {\n\t\treturn str\n\t\t\t.replace(/[-_](.)/g, (_, c) => c.toUpperCase())\n\t\t\t.replace(/^./, (c) => c.toUpperCase());\n\t}\n\n\t/**\n\t * Convert schema to interface while collecting $defs for nested schemas\n\t * with .meta({ id: 'X' }).\n\t */\n\tprivate async schemaToInterfaceWithDefs(\n\t\tschema: StandardSchemaV1,\n\t\tname: string,\n\t\tcollectedDefs: Map<string, JsonSchema>,\n\t): Promise<string | null> {\n\t\ttry {\n\t\t\t// Get raw JSON schema with $defs intact (don't use convertStandardSchemaToJsonSchema\n\t\t\t// which strips $defs)\n\t\t\tconst vendor = schema['~standard']?.vendor;\n\t\t\tif (!vendor || !(vendor in StandardSchemaJsonSchema)) {\n\t\t\t\treturn null;\n\t\t\t}\n\n\t\t\tconst toJsonSchema =\n\t\t\t\tStandardSchemaJsonSchema[\n\t\t\t\t\tvendor as keyof typeof StandardSchemaJsonSchema\n\t\t\t\t];\n\t\t\tconst jsonSchema = await toJsonSchema(schema);\n\t\t\tif (!jsonSchema) return null;\n\n\t\t\t// Extract $defs from the JSON schema (these come from .meta({ id: 'X' }))\n\t\t\tif (jsonSchema.$defs && typeof jsonSchema.$defs === 'object') {\n\t\t\t\tfor (const [defName, defSchema] of Object.entries(jsonSchema.$defs)) {\n\t\t\t\t\tif (!collectedDefs.has(defName)) {\n\t\t\t\t\t\t// Remove the 'id' field from the schema as it's just metadata\n\t\t\t\t\t\tconst { id, ...schemaWithoutId } = defSchema as JsonSchema & {\n\t\t\t\t\t\t\tid?: string;\n\t\t\t\t\t\t};\n\t\t\t\t\t\tcollectedDefs.set(defName, schemaWithoutId as JsonSchema);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Remove $defs from the schema before converting to interface\n\t\t\tconst { $defs, ...schemaWithoutDefs } = jsonSchema;\n\n\t\t\t// A schema that *is* a registered schema converts to nothing but a\n\t\t\t// `$ref` at it, and the def it points at has already been collected\n\t\t\t// above — so emitting a declaration here as well produces\n\t\t\t// `export type User = User`, a circular alias that is not a type.\n\t\t\t//\n\t\t\t// Zod used to inline this case and only started emitting the `$ref` in\n\t\t\t// 4.6, which is how the bug arrived without the generator changing.\n\t\t\tconst ref = (schemaWithoutDefs as { $ref?: string }).$ref;\n\t\t\tif (\n\t\t\t\tref &&\n\t\t\t\tObject.keys(schemaWithoutDefs).every(\n\t\t\t\t\t(k) => k === '$ref' || k === '$schema',\n\t\t\t\t)\n\t\t\t) {\n\t\t\t\tconst target = ref.split('/').pop();\n\t\t\t\t// The def's own interface is the declaration. Only alias it when the\n\t\t\t\t// names actually differ, which is when the alias says something.\n\t\t\t\treturn target === name ? null : `export type ${name} = ${target};`;\n\t\t\t}\n\n\t\t\treturn this.jsonSchemaToInterface(schemaWithoutDefs, name);\n\t\t} catch {\n\t\t\treturn null;\n\t\t}\n\t}\n\n\tprivate jsonSchemaToInterface(schema: JsonSchema, name: string): string {\n\t\tif (schema.type !== 'object' || !schema.properties) {\n\t\t\t// For non-object types, create a type alias\n\t\t\tconst typeStr = this.jsonSchemaTypeToTs(schema);\n\t\t\treturn `export type ${name} = ${typeStr};`;\n\t\t}\n\n\t\tconst props: string[] = [];\n\t\tconst required = new Set(schema.required || []);\n\n\t\tfor (const [propName, propSchema] of Object.entries(schema.properties)) {\n\t\t\tconst isRequired = required.has(propName);\n\t\t\tconst typeStr = this.jsonSchemaTypeToTs(propSchema as JsonSchema);\n\t\t\tconst optionalMark = isRequired ? '' : '?';\n\t\t\tprops.push(` ${propName}${optionalMark}: ${typeStr};`);\n\t\t}\n\n\t\treturn `export interface ${name} {\\n${props.join('\\n')}\\n}`;\n\t}\n\n\tprivate jsonSchemaTypeToTs(schema: JsonSchema): string {\n\t\tif (!schema) return 'unknown';\n\n\t\tif (schema.$ref) {\n\t\t\t// Extract name from $ref\n\t\t\tconst refName = schema.$ref.split('/').pop() || 'unknown';\n\t\t\treturn refName;\n\t\t}\n\n\t\tif (schema.anyOf) {\n\t\t\treturn schema.anyOf\n\t\t\t\t.map((s: JsonSchema) => this.jsonSchemaTypeToTs(s))\n\t\t\t\t.join(' | ');\n\t\t}\n\n\t\tif (schema.oneOf) {\n\t\t\treturn schema.oneOf\n\t\t\t\t.map((s: JsonSchema) => this.jsonSchemaTypeToTs(s))\n\t\t\t\t.join(' | ');\n\t\t}\n\n\t\tif (schema.allOf) {\n\t\t\treturn schema.allOf\n\t\t\t\t.map((s: JsonSchema) => this.jsonSchemaTypeToTs(s))\n\t\t\t\t.join(' & ');\n\t\t}\n\n\t\tswitch (schema.type) {\n\t\t\tcase 'string':\n\t\t\t\tif (schema.enum) {\n\t\t\t\t\treturn schema.enum.map((e: string) => `'${e}'`).join(' | ');\n\t\t\t\t}\n\t\t\t\treturn 'string';\n\t\t\tcase 'number':\n\t\t\tcase 'integer':\n\t\t\t\treturn 'number';\n\t\t\tcase 'boolean':\n\t\t\t\treturn 'boolean';\n\t\t\tcase 'null':\n\t\t\t\treturn 'null';\n\t\t\tcase 'array':\n\t\t\t\tif (schema.items) {\n\t\t\t\t\treturn `Array<${this.jsonSchemaTypeToTs(schema.items as JsonSchema)}>`;\n\t\t\t\t}\n\t\t\t\treturn 'Array<unknown>';\n\t\t\tcase 'object':\n\t\t\t\tif (schema.properties) {\n\t\t\t\t\tconst props: string[] = [];\n\t\t\t\t\tconst required = new Set(schema.required || []);\n\t\t\t\t\tfor (const [propName, propSchema] of Object.entries(\n\t\t\t\t\t\tschema.properties,\n\t\t\t\t\t)) {\n\t\t\t\t\t\tconst isRequired = required.has(propName);\n\t\t\t\t\t\tconst typeStr = this.jsonSchemaTypeToTs(propSchema as JsonSchema);\n\t\t\t\t\t\tconst optionalMark = isRequired ? '' : '?';\n\t\t\t\t\t\tprops.push(`${propName}${optionalMark}: ${typeStr}`);\n\t\t\t\t\t}\n\t\t\t\t\treturn `{ ${props.join('; ')} }`;\n\t\t\t\t}\n\t\t\t\tif (schema.additionalProperties) {\n\t\t\t\t\tconst valueType = this.jsonSchemaTypeToTs(\n\t\t\t\t\t\tschema.additionalProperties as JsonSchema,\n\t\t\t\t\t);\n\t\t\t\t\treturn `Record<string, ${valueType}>`;\n\t\t\t\t}\n\t\t\t\treturn 'Record<string, unknown>';\n\t\t\tdefault:\n\t\t\t\treturn 'unknown';\n\t\t}\n\t}\n\n\tprivate async generatePathsInterface(\n\t\tendpointInfos: EndpointInfo[],\n\t): Promise<string> {\n\t\tconst pathGroups = new Map<string, EndpointInfo[]>();\n\n\t\t// Group endpoints by route\n\t\tfor (const info of endpointInfos) {\n\t\t\tconst existing = pathGroups.get(info.route) || [];\n\t\t\texisting.push(info);\n\t\t\tpathGroups.set(info.route, existing);\n\t\t}\n\n\t\tconst pathEntries: string[] = [];\n\n\t\tfor (const [route, infos] of pathGroups) {\n\t\t\tconst methodEntries: string[] = [];\n\n\t\t\tfor (const info of infos) {\n\t\t\t\tconst methodDef = await this.generateMethodDefinition(info);\n\t\t\t\tmethodEntries.push(` ${info.method.toLowerCase()}: ${methodDef};`);\n\t\t\t}\n\n\t\t\t// Add path parameters if present\n\t\t\tconst firstWithParams = infos.find((i) => i.input?.params);\n\t\t\tlet paramsEntry = '';\n\t\t\tif (firstWithParams?.input?.params) {\n\t\t\t\tconst paramsName = await this.getSchemaName(\n\t\t\t\t\tfirstWithParams.input.params,\n\t\t\t\t\t`${this.getSchemaBaseName(firstWithParams)}Params`,\n\t\t\t\t);\n\t\t\t\tparamsEntry = `\\n parameters: {\\n path: ${paramsName};\\n };`;\n\t\t\t}\n\n\t\t\tpathEntries.push(\n\t\t\t\t` '${route}': {${paramsEntry}\\n${methodEntries.join('\\n')}\\n };`,\n\t\t\t);\n\t\t}\n\n\t\treturn `export interface paths {\\n${pathEntries.join('\\n')}\\n}`;\n\t}\n\n\tprivate async generateMethodDefinition(info: EndpointInfo): Promise<string> {\n\t\tconst parts: string[] = [];\n\t\tconst baseName = this.getSchemaBaseName(info);\n\n\t\t// Request body\n\t\tif (info.input?.body) {\n\t\t\tconst bodyName = await this.getSchemaName(\n\t\t\t\tinfo.input.body,\n\t\t\t\t`${baseName}Input`,\n\t\t\t);\n\t\t\tparts.push(`requestBody: {\n content: {\n 'application/json': ${bodyName};\n };\n }`);\n\t\t}\n\n\t\t// Query parameters\n\t\tif (info.input?.query) {\n\t\t\tconst queryName = await this.getSchemaName(\n\t\t\t\tinfo.input.query,\n\t\t\t\t`${baseName}Query`,\n\t\t\t);\n\t\t\tparts.push(`parameters: {\n query: ${queryName};\n }`);\n\t\t}\n\n\t\t// Responses\n\t\tconst outputName = info.output\n\t\t\t? await this.getSchemaName(info.output, `${baseName}Output`)\n\t\t\t: 'unknown';\n\t\tparts.push(`responses: {\n 200: {\n content: {\n '${info.responseType}': ${outputName};\n };\n };\n }`);\n\n\t\treturn `{\\n ${parts.join(';\\n ')};\\n }`;\n\t}\n\n\tprivate buildModule(params: {\n\t\ttitle: string;\n\t\tversion: string;\n\t\tdescription?: string;\n\t\tsecuritySchemes: SecuritySchemeInfo[];\n\t\tendpointAuth: Record<string, string | null>;\n\t\tschemaInterfaces: string;\n\t\tpathsInterface: string;\n\t}): string {\n\t\tconst {\n\t\t\ttitle,\n\t\t\tversion,\n\t\t\tdescription,\n\t\t\tsecuritySchemes,\n\t\t\tendpointAuth,\n\t\t\tschemaInterfaces,\n\t\t\tpathsInterface,\n\t\t} = params;\n\n\t\tconst securitySchemesObj = securitySchemes.reduce(\n\t\t\t(acc, s) => {\n\t\t\t\tacc[s.name] = s.scheme;\n\t\t\t\treturn acc;\n\t\t\t},\n\t\t\t{} as Record<string, SecuritySchemeObject>,\n\t\t);\n\n\t\tconst schemeNames = securitySchemes.map((s) => `'${s.name}'`).join(' | ');\n\n\t\t// Generate createApi only if there are security schemes\n\t\tconst hasSecuritySchemes = schemeNames.length > 0;\n\n\t\tconst createApiSection = hasSecuritySchemes\n\t\t\t? `\n// ============================================================\n// API Client Factory\n// ============================================================\n\nimport {\n createAuthAwareFetcher,\n type AuthStrategy,\n} from '@geekmidas/client/auth-fetcher';\nimport { createEndpointHooks } from '@geekmidas/client/endpoint-hooks';\nimport type { QueryClient } from '@tanstack/react-query';\n\n/**\n * Options for creating the API client.\n */\nexport interface CreateApiOptions {\n /** Base URL for all API requests (required) */\n baseURL: string;\n /** Auth strategies for each security scheme used in this API */\n authStrategies: Record<SecuritySchemeId, AuthStrategy>;\n /** Optional React Query client instance */\n queryClient?: QueryClient;\n /** Optional request interceptor */\n onRequest?: (config: RequestInit) => RequestInit | Promise<RequestInit>;\n}\n\n/**\n * Create a type-safe API client with authentication and React Query hooks.\n *\n * @example\n * \\`\\`\\`typescript\n * const api = createApi({\n * baseURL: 'https://api.example.com',\n * authStrategies: {\n * jwt: { type: 'bearer', tokenProvider },\n * },\n * });\n *\n * // Imperative fetch\n * const user = await api('GET /users/{id}', { params: { id: '123' } });\n *\n * // React Query hooks\n * const { data } = api.useQuery('GET /users/{id}', { params: { id: '123' } });\n * const mutation = api.useMutation('POST /users');\n * \\`\\`\\`\n */\nexport function createApi(options: CreateApiOptions) {\n const fetcher = createAuthAwareFetcher<paths, typeof endpointAuth, typeof securitySchemes>({\n baseURL: options.baseURL,\n endpointAuth,\n securitySchemes,\n authStrategies: options.authStrategies,\n onRequest: options.onRequest,\n });\n\n const hooks = createEndpointHooks<paths>(fetcher, { queryClient: options.queryClient });\n\n return Object.assign(fetcher, hooks);\n}\n`\n\t\t\t: `\n// ============================================================\n// API Client Factory\n// ============================================================\n\nimport { createTypedFetcher, type FetcherOptions } from '@geekmidas/client/fetcher';\nimport { createEndpointHooks } from '@geekmidas/client/endpoint-hooks';\nimport type { QueryClient } from '@tanstack/react-query';\n\n/**\n * Options for creating the API client.\n */\nexport interface CreateApiOptions extends Omit<FetcherOptions, 'baseURL'> {\n /** Base URL for all API requests (required) */\n baseURL: string;\n /** Optional React Query client instance */\n queryClient?: QueryClient;\n}\n\n/**\n * Create a type-safe API client with React Query hooks.\n *\n * @example\n * \\`\\`\\`typescript\n * const api = createApi({\n * baseURL: 'https://api.example.com',\n * });\n *\n * // Imperative fetch\n * const data = await api('GET /health');\n *\n * // React Query hooks\n * const { data } = api.useQuery('GET /health');\n * \\`\\`\\`\n */\nexport function createApi(options: CreateApiOptions) {\n const { queryClient, ...fetcherOptions } = options;\n const request = createTypedFetcher<paths>(fetcherOptions);\n\n const hooks = createEndpointHooks<paths>(request, { queryClient });\n\n return Object.assign(request, hooks);\n}\n`;\n\n\t\treturn `// Auto-generated by @geekmidas/cli - DO NOT EDIT\n\n// ============================================================\n// Security Scheme Type\n// ============================================================\n\ninterface SecuritySchemeObject {\n type: 'apiKey' | 'http' | 'mutualTLS' | 'oauth2' | 'openIdConnect';\n description?: string;\n name?: string;\n in?: 'query' | 'header' | 'cookie';\n scheme?: string;\n bearerFormat?: string;\n flows?: Record<string, unknown>;\n openIdConnectUrl?: string;\n [key: string]: unknown;\n}\n\n// ============================================================\n// API Info\n// ============================================================\n\nexport const apiInfo = {\n title: '${title}',\n version: '${version}',${description ? `\\n description: '${description.replace(/'/g, \"\\\\'\")}',` : ''}\n} as const;\n\n// ============================================================\n// Security Schemes\n// ============================================================\n\n/**\n * Available security schemes for this API.\n * Maps authorizer names to OpenAPI security scheme definitions.\n */\nexport const securitySchemes = ${JSON.stringify(securitySchemesObj, null, 2).replace(/\"([a-zA-Z_$][a-zA-Z0-9_$]*)\":/g, '$1:')} as const satisfies Record<string, SecuritySchemeObject>;\n\nexport type SecuritySchemeId = ${schemeNames || 'never'};\n\n// ============================================================\n// Endpoint Authentication Map\n// ============================================================\n\n/**\n * Runtime map of endpoints to their required authentication scheme.\n * \\`null\\` indicates a public endpoint (no auth required).\n */\nexport const endpointAuth = ${JSON.stringify(endpointAuth, null, 2).replace(/\"([^\"]+)\":/g, \"'$1':\")} as const satisfies Record<string, SecuritySchemeId | null>;\n\nexport type EndpointString = keyof typeof endpointAuth;\n\nexport type AuthenticatedEndpoint = {\n [K in EndpointString]: typeof endpointAuth[K] extends null ? never : K;\n}[EndpointString];\n\nexport type PublicEndpoint = {\n [K in EndpointString]: typeof endpointAuth[K] extends null ? K : never;\n}[EndpointString];\n\n// ============================================================\n// Schema Definitions\n// ============================================================\n\n${schemaInterfaces}\n\n// ============================================================\n// OpenAPI Paths\n// ============================================================\n\n${pathsInterface}\n${createApiSection}\n`;\n\t}\n}\n","import { join } from 'node:path';\nimport { isPartitionedRoutes, type Routes } from '../types.js';\nimport type { NormalizedWorkspace } from './types.js';\n\n/**\n * Normalize routes to an array of patterns.\n * Handles string, string[], and PartitionedRoutes (extracts paths).\n * @internal Exported for use in dev command\n */\nexport function normalizeRoutes(routes: Routes | undefined): string[] {\n\tif (!routes) return [];\n\tif (isPartitionedRoutes(routes)) {\n\t\treturn Array.isArray(routes.paths) ? routes.paths : [routes.paths];\n\t}\n\treturn Array.isArray(routes) ? routes : [routes];\n}\n\n/**\n * Get the first routes pattern as a string (for simple cases).\n * @internal Exported for use in dev command\n */\nexport function getFirstRoute(\n\troutes: string | string[] | undefined,\n): string | null {\n\tconst normalized = normalizeRoutes(routes);\n\treturn normalized[0] || null;\n}\n\n/**\n * Check if a file path matches endpoint patterns that could affect OpenAPI schema.\n * Returns true for changes that should trigger client regeneration.\n */\nexport function shouldRegenerateClient(\n\tfilePath: string,\n\troutesPattern: string,\n): boolean {\n\t// Normalize path separators\n\tconst normalizedPath = filePath.replace(/\\\\/g, '/');\n\tconst normalizedPattern = routesPattern.replace(/\\\\/g, '/');\n\n\t// Check if the file matches the routes pattern\n\t// This is a simple check - the file should be within the routes directory\n\tconst patternDir = normalizedPattern.split('*')[0] || '';\n\n\tif (!normalizedPath.includes(patternDir.replace('./', ''))) {\n\t\treturn false;\n\t}\n\n\t// Check file extension - only TypeScript endpoint files\n\tif (!normalizedPath.endsWith('.ts') && !normalizedPath.endsWith('.tsx')) {\n\t\treturn false;\n\t}\n\n\treturn true;\n}\n\n/**\n * Get backend apps that a web/mobile client depends on.\n */\nexport function getBackendDependencies(\n\tworkspace: NormalizedWorkspace,\n\tclientAppName: string,\n): string[] {\n\tconst clientApp = workspace.apps[clientAppName];\n\tif (!clientApp || (clientApp.type !== 'web' && clientApp.type !== 'mobile')) {\n\t\treturn [];\n\t}\n\n\treturn clientApp.dependencies.filter((dep) => {\n\t\tconst depApp = workspace.apps[dep];\n\t\treturn depApp?.type === 'backend' && depApp.routes;\n\t});\n}\n\n/**\n * Get web/mobile apps that depend on a backend app.\n */\nexport function getDependentFrontends(\n\tworkspace: NormalizedWorkspace,\n\tbackendAppName: string,\n): string[] {\n\tconst dependentApps: string[] = [];\n\n\tfor (const [appName, app] of Object.entries(workspace.apps)) {\n\t\tif (\n\t\t\t(app.type === 'web' || app.type === 'mobile') &&\n\t\t\tapp.dependencies.includes(backendAppName)\n\t\t) {\n\t\t\tdependentApps.push(appName);\n\t\t}\n\t}\n\n\treturn dependentApps;\n}\n\n/**\n * Get the path to a backend's OpenAPI spec file.\n */\nexport function getBackendOpenApiPath(\n\tworkspace: NormalizedWorkspace,\n\tbackendAppName: string,\n): string | null {\n\tconst app = workspace.apps[backendAppName];\n\tif (!app || app.type !== 'backend') {\n\t\treturn null;\n\t}\n\n\treturn join(workspace.root, app.path, '.gkm', 'openapi.ts');\n}\n","#!/usr/bin/env -S npx tsx\n\nimport { spawn } from 'node:child_process';\nimport { mkdir, writeFile } from 'node:fs/promises';\nimport { dirname, join } from 'node:path';\nimport { fileURLToPath } from 'node:url';\nimport { loadWorkspaceConfig } from './config.js';\nimport { EndpointGenerator } from './generators/EndpointGenerator.js';\nimport { OpenApiTsGenerator } from './generators/OpenApiTsGenerator.js';\nimport type { GkmConfig, OpenApiConfig } from './types.js';\nimport { normalizeRoutes } from './workspace/client-generator.js';\nimport type { NormalizedAppConfig } from './workspace/types.js';\n\ninterface OpenAPIOptions {\n\tcwd?: string;\n\t/**\n\t * Workspace mode: generate for a single named backend app. When set,\n\t * generation runs in-process against the current CWD. When unset,\n\t * workspace mode spawns one subprocess per backend app so each gets a\n\t * fresh tsx that loads the app's own tsconfig (path aliases included).\n\t */\n\tapp?: string;\n}\n\n/**\n * Default output path for generated OpenAPI client (used for single-app configs)\n */\nexport const OPENAPI_OUTPUT_PATH = './.gkm/openapi.ts';\n\n/**\n * Resolve OpenAPI config from GkmConfig\n */\nexport function resolveOpenApiConfig(\n\tconfig: GkmConfig,\n): OpenApiConfig & { enabled: boolean } {\n\tif (config.openapi === false) {\n\t\treturn { enabled: false };\n\t}\n\n\tif (config.openapi === true || config.openapi === undefined) {\n\t\t// Enable by default when not explicitly set (undefined) or explicitly true\n\t\treturn {\n\t\t\tenabled: true,\n\t\t\ttitle: 'API Documentation',\n\t\t\tversion: '1.0.0',\n\t\t\tdescription: 'Auto-generated API documentation from endpoints',\n\t\t};\n\t}\n\n\treturn {\n\t\tenabled: config.openapi.enabled !== false,\n\t\ttitle: config.openapi.title || 'API Documentation',\n\t\tversion: config.openapi.version || '1.0.0',\n\t\tdescription:\n\t\t\tconfig.openapi.description ||\n\t\t\t'Auto-generated API documentation from endpoints',\n\t};\n}\n\n/**\n * Generate OpenAPI spec from endpoints\n * @returns Object with output path and endpoint count, or null if disabled\n */\nexport async function generateOpenApi(\n\tconfig: GkmConfig,\n\toptions: { silent?: boolean; bustCache?: boolean } = {},\n): Promise<{ outputPath: string; endpointCount: number } | null> {\n\tconst logger = options.silent ? { log: () => {} } : console;\n\tconst openApiConfig = resolveOpenApiConfig(config);\n\n\tif (!openApiConfig.enabled) {\n\t\treturn null;\n\t}\n\n\tconst endpointGenerator = new EndpointGenerator();\n\tconst loadedEndpoints = await endpointGenerator.load(\n\t\tconfig.routes,\n\t\tundefined,\n\t\toptions.bustCache,\n\t);\n\n\tif (loadedEndpoints.length === 0) {\n\t\tlogger.log('No valid endpoints found for OpenAPI generation');\n\t\treturn null;\n\t}\n\n\tconst endpoints = loadedEndpoints.map(({ construct }) => construct);\n\tconst outputPath = join(process.cwd(), OPENAPI_OUTPUT_PATH);\n\n\tawait mkdir(dirname(outputPath), { recursive: true });\n\n\tconst tsGenerator = new OpenApiTsGenerator();\n\tconst tsContent = await tsGenerator.generate(endpoints, {\n\t\ttitle: openApiConfig.title!,\n\t\tversion: openApiConfig.version!,\n\t\tdescription: openApiConfig.description!,\n\t});\n\n\tawait writeFile(outputPath, tsContent);\n\tlogger.log(`📄 OpenAPI client generated: ${OPENAPI_OUTPUT_PATH}`);\n\n\treturn { outputPath, endpointCount: loadedEndpoints.length };\n}\n\nexport async function openapiCommand(\n\toptions: OpenAPIOptions = {},\n): Promise<void> {\n\tconst logger = console;\n\n\ttry {\n\t\tconst loadedConfig = await loadWorkspaceConfig(options.cwd);\n\n\t\tif (loadedConfig.type === 'single') {\n\t\t\t// Single-app config - use existing behavior\n\t\t\tconst config = loadedConfig.raw as GkmConfig;\n\n\t\t\t// Enable openapi if not configured\n\t\t\tif (!config.openapi) {\n\t\t\t\tconfig.openapi = { enabled: true };\n\t\t\t}\n\n\t\t\tconst result = await generateOpenApi(config);\n\n\t\t\tif (result) {\n\t\t\t\tlogger.log(`Found ${result.endpointCount} endpoints`);\n\t\t\t}\n\t\t} else {\n\t\t\t// Workspace config - generate for each backend app\n\t\t\tconst { workspace } = loadedConfig;\n\t\t\t// Always derive the workspace root from the loaded config rather than\n\t\t\t// CWD. Subprocesses run with CWD set to an app directory, and falling\n\t\t\t// back to CWD there causes `join(workspaceRoot, app.path)` to point at\n\t\t\t// a non-existent nested path (e.g. `apps/api/apps/api`).\n\t\t\tconst workspaceRoot = workspace.root;\n\n\t\t\t// Backend apps with openapi enabled — which is all of them that have\n\t\t\t// routes, unless one says otherwise.\n\t\t\t//\n\t\t\t// This used to require `openapi: true` written out, while the app's\n\t\t\t// own build generated a spec regardless. Two paths disagreeing about\n\t\t\t// the same flag: the app emitted `.gkm/openapi.ts` and this pass,\n\t\t\t// finding nothing \"enabled\", skipped copying it to the frontends that\n\t\t\t// consume it. A surface whose routes are declared rather than\n\t\t\t// discovered has no spec to generate, so it is not a candidate.\n\t\t\tconst backendApps = Object.entries(workspace.apps).filter(\n\t\t\t\t([_, app]) =>\n\t\t\t\t\tapp.type === 'backend' &&\n\t\t\t\t\tapp.routes !== undefined &&\n\t\t\t\t\tapp.openapi !== false &&\n\t\t\t\t\t(typeof app.openapi !== 'object' || app.openapi.enabled !== false),\n\t\t\t);\n\n\t\t\tif (backendApps.length === 0) {\n\t\t\t\tlogger.log('No backend apps with OpenAPI enabled found');\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// Single-app mode: generate in-process. The caller is expected to\n\t\t\t// have CWD set to the app's directory (e.g., when invoked as a\n\t\t\t// subprocess), so tsx picks up the app's tsconfig path aliases.\n\t\t\tif (options.app) {\n\t\t\t\tconst entry = backendApps.find(([name]) => name === options.app);\n\t\t\t\tif (!entry) {\n\t\t\t\t\tthrow new Error(\n\t\t\t\t\t\t`App \"${options.app}\" not found or has OpenAPI disabled`,\n\t\t\t\t\t);\n\t\t\t\t}\n\t\t\t\tconst [appName, app] = entry;\n\t\t\t\tconst result = await generateOpenApiForApp(workspaceRoot, appName, app);\n\t\t\t\tif (result) {\n\t\t\t\t\tlogger.log(\n\t\t\t\t\t\t`📄 [${appName}] Generated OpenAPI (${result.endpointCount} endpoints)`,\n\t\t\t\t\t);\n\t\t\t\t}\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// Multi-app mode: spawn a subprocess per backend app. Each\n\t\t\t// subprocess starts with CWD at the app's directory so that\n\t\t\t// tsx's tsconfig discovery picks up the app's `paths` aliases\n\t\t\t// (e.g., `~/*`) instead of the workspace root's tsconfig.\n\t\t\tfor (const [appName, app] of backendApps) {\n\t\t\t\tif (app.type !== 'backend' || !app.routes) continue;\n\t\t\t\tconst appPath = join(workspaceRoot, app.path);\n\t\t\t\tawait runOpenApiInSubprocess(appPath, appName);\n\t\t\t}\n\t\t}\n\t} catch (error) {\n\t\tthrow new Error(`OpenAPI generation failed: ${(error as Error).message}`);\n\t}\n}\n\n/**\n * Generate OpenAPI for a single named app within a workspace.\n * Runs in-process. The caller is responsible for ensuring `process.cwd()`\n * is the app's directory so tsx loads the app's tsconfig path aliases.\n */\nasync function generateOpenApiForApp(\n\tworkspaceRoot: string,\n\t_appName: string,\n\tapp: NormalizedAppConfig,\n): Promise<{ outputPath: string; endpointCount: number } | null> {\n\tif (app.type !== 'backend' || !app.routes) {\n\t\treturn null;\n\t}\n\n\tconst appPath = join(workspaceRoot, app.path);\n\tconst routes = normalizeRoutes(app.routes);\n\tconst routesGlob = routes.map((r) => join(appPath, r));\n\n\tconst gkmConfig: GkmConfig = {\n\t\troutes: routesGlob,\n\t\tenvParser: app.envParser || '',\n\t\tlogger: app.logger || '',\n\t\topenapi: app.openapi,\n\t};\n\n\treturn generateOpenApi(gkmConfig, { silent: true });\n}\n\n/**\n * Resolve the gkm bin path. Tests can override via `GKM_BIN_PATH` env var\n * to avoid depending on the built dist.\n */\nfunction resolveGkmBinPath(): string {\n\tif (process.env.GKM_BIN_PATH) {\n\t\treturn process.env.GKM_BIN_PATH;\n\t}\n\treturn fileURLToPath(new URL('../bin/gkm.mjs', import.meta.url));\n}\n\n/**\n * Spawn a subprocess that runs `gkm openapi --app <name>` with `cwd` set to\n * the app's directory. Inherits `NODE_OPTIONS` (which already contains\n * `--import tsx`), so the child gets a fresh tsx instance whose tsconfig\n * discovery picks up the app's tsconfig path aliases.\n */\nasync function runOpenApiInSubprocess(\n\tappCwd: string,\n\tappName: string,\n): Promise<void> {\n\tconst binPath = resolveGkmBinPath();\n\n\tawait new Promise<void>((resolve, reject) => {\n\t\tconst child = spawn(\n\t\t\tprocess.execPath,\n\t\t\t[binPath, 'openapi', '--app', appName],\n\t\t\t{\n\t\t\t\tcwd: appCwd,\n\t\t\t\tstdio: 'inherit',\n\t\t\t\tenv: process.env,\n\t\t\t},\n\t\t);\n\n\t\tchild.on('error', reject);\n\t\tchild.on('close', (code) => {\n\t\t\tif (code === 0) {\n\t\t\t\tresolve();\n\t\t\t} else {\n\t\t\t\treject(\n\t\t\t\t\tnew Error(\n\t\t\t\t\t\t`OpenAPI generation for app \"${appName}\" exited with code ${code}`,\n\t\t\t\t\t),\n\t\t\t\t);\n\t\t\t}\n\t\t});\n\t});\n}\n"],"mappings":"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"}
@@ -1,11 +0,0 @@
1
- require('./discover-DTmFeloL.cjs');
2
- require('./config-C21ocYNd.cjs');
3
- require('./workspace-BcucjwvA.cjs');
4
- require('./credentials-G1JwBoXH.cjs');
5
- require('./generator-CNzBw7g5.cjs');
6
- require('./storage-BJmzYxt8.cjs');
7
- require('./fullstack-secrets-C-GGohke.cjs');
8
- require('./sync-SizaChmC.cjs');
9
- const require_setup = require('./setup-Cm2UnAdh.cjs');
10
-
11
- exports.ensureStageSecrets = require_setup.ensureStageSecrets;
@@ -1,8 +0,0 @@
1
- import "./discover-CAlFgYec.mjs";
2
- import "./config-WRdsQYZK.mjs";
3
- import "./workspace-BFMrAKqI.mjs";
4
- import { constructGlobs, derivedContainers, imagePins, reconcileWorkspace, usesConstructs } from "./credentials-BBIRJVp4.mjs";
5
- import "./generator-VE2JrFlY.mjs";
6
- import "./storage-Bi24WfoW.mjs";
7
-
8
- export { derivedContainers, reconcileWorkspace };