import { existsSync, readFileSync } from 'node:fs'; import { dirname, join } from 'node:path'; import { fileURLToPath } from 'node:url'; const root = dirname(fileURLToPath(new URL('../package.json', import.meta.url))); const checks = [ { file: 'Dockerfile.web', snippets: [ 'FROM node:20-alpine', 'pnpm --filter @ftb/shared build', 'pnpm --filter web build', 'NEXT_PUBLIC_API_URL', 'CMD ["pnpm", "--filter", "web", "start"]', ], }, { file: 'Dockerfile.server', snippets: [ 'FROM node:20-alpine', 'pnpm --filter @ftb/shared build', 'pnpm --filter server build', 'prisma generate', 'CMD ["pnpm", "--filter", "server", "start:prod"]', ], }, { file: 'docker-compose.prod.yml', snippets: [ 'web:', 'server:', 'postgres:', 'redis:', 'nginx:', 'server_data:', 'NEXT_PUBLIC_API_URL', '/api/v1/config/ai', ], }, { file: 'docker-compose.local.yml', snippets: [ 'web:', 'server:', 'postgres:', 'redis:', 'nginx:', 'local_server_data:', 'NEXT_PUBLIC_API_URL', '${LOCAL_HTTP_PORT:-8080}:80', ], }, { file: 'deploy/nginx/default.conf.template', snippets: [ 'proxy_pass http://web:3000', 'proxy_pass http://server:3001', 'client_max_body_size', 'X-Forwarded-Proto', ], }, { file: '.env.production.example', snippets: [ 'POSTGRES_PASSWORD=', 'DATABASE_URL=postgresql://', 'NEXT_PUBLIC_API_URL=', 'NEXTAUTH_SECRET=', 'ANTHROPIC_API_KEY=', ], }, { file: '.env.local-server.example', snippets: [ 'LOCAL_HTTP_PORT=8080', 'LOCAL_ACCESS_HOST=localhost', 'DATABASE_URL=postgresql://', 'NEXT_PUBLIC_API_URL=/api/v1', 'NEXTAUTH_URL=http://localhost:8080', ], }, { file: 'docs/deployment.md', snippets: [ 'docker-compose.prod.yml', 'docker-compose.local.yml', '本地服务器部署', 'pnpm deploy:verify', 'pnpm db:migrate', 'NEXT_PUBLIC_API_URL', 'Nginx', ], }, ]; let failed = false; for (const check of checks) { const abs = join(root, check.file); if (!existsSync(abs)) { console.error(`Missing deployment artifact: ${check.file}`); failed = true; continue; } const content = readFileSync(abs, 'utf8'); for (const snippet of check.snippets) { if (!content.includes(snippet)) { console.error(`Missing snippet in ${check.file}: ${snippet}`); failed = true; } } } if (failed) { process.exit(1); } console.log('Production deployment artifacts verified.');