Docker 容器化 Node.js 应用
为什么容器化
容器化解决了"在我机器上能跑"的经典问题。通过将应用和运行环境打包在一起,确保开发、测试、生产环境的一致性,也让水平扩展变得简单。
多阶段构建 Dockerfile
# 构建阶段
FROM node:20-alpine AS builder
WORKDIR /app
COPY package*.json ./
RUN npm ci --only=production
COPY . .
RUN npm run build
# 运行阶段
FROM node:20-alpine AS runner
WORKDIR /app
# 非 root 用户,增强安全性
RUN addgroup --system --gid 1001 nodejs
RUN adduser --system --uid 1001 nextjs
USER nextjs
COPY --from=builder --chown=nextjs:nodejs /app/.next ./.next
COPY --from=builder /app/node_modules ./node_modules
COPY --from=builder /app/package.json ./package.json
EXPOSE 3000
CMD ["npm", "start"]
docker-compose 本地开发
services:
app:
build: .
ports:
- "3000:3000"
environment:
- DATABASE_URL=postgresql://postgres:password@db:5432/myapp
depends_on:
db:
condition: service_healthy
db:
image: postgres:16-alpine
environment:
POSTGRES_PASSWORD: password
POSTGRES_DB: myapp
healthcheck:
test: ["CMD-SHELL", "pg_isready -U postgres"]
interval: 5s
timeout: 5s
retries: 5
常用调试命令
# 查看容器日志
docker logs -f container-name
# 进入容器 shell
docker exec -it container-name sh
# 清理未使用的镜像
docker system prune -a
总结
多阶段构建是生产环境 Dockerfile 的标配,可以将镜像体积从 1GB+ 压缩到 100MB 以内。配合非 root 用户和只读文件系统,能显著提升容器运行时的安全性。