|
| 1 | +import { readFileSync, writeFileSync } from 'node:fs'; |
| 2 | +import { resolve } from 'node:path'; |
| 3 | + |
| 4 | +const root = process.cwd(); |
| 5 | +const examplePath = resolve(root, '.env.example'); |
| 6 | +const outputPath = resolve(root, 'lib/env/runtime-env.generated.ts'); |
| 7 | + |
| 8 | +const keyRegex = /^([A-Z][A-Z0-9_]*)=/; |
| 9 | + |
| 10 | +const keys = Array.from( |
| 11 | + new Set( |
| 12 | + readFileSync(examplePath, 'utf8') |
| 13 | + .split(/\r?\n/) |
| 14 | + .map(line => line.trim()) |
| 15 | + .filter(line => line && !line.startsWith('#')) |
| 16 | + .map(line => { |
| 17 | + const match = line.match(keyRegex); |
| 18 | + return match ? match[1] : null; |
| 19 | + }) |
| 20 | + .filter(Boolean) |
| 21 | + ) |
| 22 | +); |
| 23 | + |
| 24 | +const entries = []; |
| 25 | + |
| 26 | +for (const key of keys) { |
| 27 | + const value = process.env[key]; |
| 28 | + if (typeof value !== 'string' || value.length === 0) continue; |
| 29 | + entries.push([key, value]); |
| 30 | +} |
| 31 | + |
| 32 | +const objectBody = entries |
| 33 | + .map(([key, value]) => ` ${JSON.stringify(key)}: ${JSON.stringify(value)},`) |
| 34 | + .join('\n'); |
| 35 | + |
| 36 | +const fileContent = `import 'server-only'; |
| 37 | +
|
| 38 | +export const RUNTIME_ENV: Readonly<Record<string, string>> = { |
| 39 | +${objectBody} |
| 40 | +}; |
| 41 | +`; |
| 42 | + |
| 43 | +writeFileSync(outputPath, fileContent, 'utf8'); |
| 44 | +console.log(`[env] generated runtime-env.generated.ts with ${entries.length} keys`); |
0 commit comments