Nuxt.js Docker部署 #
一、Docker概述 #
Docker 是一种容器化技术,可以将应用及其依赖打包成可移植的容器镜像。
1.1 Docker优势 #
- 环境一致性:开发、测试、生产环境一致
- 快速部署:秒级启动容器
- 资源隔离:独立的运行环境
- 可移植性:在任何支持 Docker 的平台运行
二、Dockerfile #
2.1 基础Dockerfile #
Dockerfile:
dockerfile
FROM node:20-alpine AS builder
WORKDIR /app
COPY package.json pnpm-lock.yaml ./
RUN npm install -g pnpm && pnpm install --frozen-lockfile
COPY . .
RUN pnpm run build
FROM node:20-alpine AS runtime
WORKDIR /app
COPY --from=builder /app/.output ./.output
ENV NUXT_HOST=0.0.0.0
ENV NUXT_PORT=3000
EXPOSE 3000
CMD ["node", ".output/server/index.mjs"]
2.2 多阶段构建 #
dockerfile
FROM node:20-alpine AS deps
WORKDIR /app
COPY package.json pnpm-lock.yaml ./
RUN npm install -g pnpm && \
pnpm install --frozen-lockfile
FROM node:20-alpine AS builder
WORKDIR /app
COPY --from=deps /app/node_modules ./node_modules
COPY . .
ENV NUXT_TELEMETRY_DISABLED=1
RUN npm install -g pnpm && \
pnpm run build
FROM node:20-alpine AS runtime
WORKDIR /app
RUN addgroup --system --gid 1001 nodejs
RUN adduser --system --uid 1001 nuxt
COPY --from=builder /app/.output ./.output
RUN chown -R nuxt:nodejs /app
USER nuxt
ENV NUXT_HOST=0.0.0.0
ENV NUXT_PORT=3000
ENV NODE_ENV=production
EXPOSE 3000
CMD ["node", ".output/server/index.mjs"]
2.3 静态站点Dockerfile #
dockerfile
FROM node:20-alpine AS builder
WORKDIR /app
COPY package.json pnpm-lock.yaml ./
RUN npm install -g pnpm && pnpm install --frozen-lockfile
COPY . .
RUN pnpm run generate
FROM nginx:alpine
COPY --from=builder /app/.output/public /usr/share/nginx/html
COPY nginx.conf /etc/nginx/conf.d/default.conf
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]
三、构建镜像 #
3.1 构建命令 #
bash
docker build -t my-nuxt-app .
3.2 指定标签 #
bash
docker build -t my-nuxt-app:v1.0.0 .
3.3 构建参数 #
bash
docker build \
--build-arg NUXT_PUBLIC_API_BASE=https://api.example.com \
-t my-nuxt-app .
四、运行容器 #
4.1 基本运行 #
bash
docker run -p 3000:3000 my-nuxt-app
4.2 环境变量 #
bash
docker run \
-p 3000:3000 \
-e NUXT_PUBLIC_API_BASE=https://api.example.com \
-e NUXT_SECRET_KEY=your-secret-key \
my-nuxt-app
4.3 后台运行 #
bash
docker run -d -p 3000:3000 --name nuxt-app my-nuxt-app
4.4 数据卷 #
bash
docker run \
-p 3000:3000 \
-v $(pwd)/logs:/app/logs \
my-nuxt-app
五、Docker Compose #
5.1 基本配置 #
docker-compose.yml:
yaml
version: '3.8'
services:
nuxt:
build: .
ports:
- "3000:3000"
environment:
- NUXT_PUBLIC_API_BASE=https://api.example.com
- NUXT_SECRET_KEY=your-secret-key
restart: unless-stopped
5.2 完整配置 #
yaml
version: '3.8'
services:
nuxt:
build:
context: .
dockerfile: Dockerfile
args:
- NUXT_PUBLIC_API_BASE=${NUXT_PUBLIC_API_BASE}
ports:
- "3000:3000"
environment:
- NUXT_HOST=0.0.0.0
- NUXT_PORT=3000
- NUXT_PUBLIC_API_BASE=${NUXT_PUBLIC_API_BASE}
- NUXT_SECRET_KEY=${NUXT_SECRET_KEY}
- DATABASE_URL=${DATABASE_URL}
depends_on:
- db
- redis
networks:
- app-network
restart: unless-stopped
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:3000/api/health"]
interval: 30s
timeout: 10s
retries: 3
db:
image: postgres:15-alpine
environment:
- POSTGRES_USER=${DB_USER}
- POSTGRES_PASSWORD=${DB_PASSWORD}
- POSTGRES_DB=${DB_NAME}
volumes:
- postgres-data:/var/lib/postgresql/data
networks:
- app-network
restart: unless-stopped
redis:
image: redis:7-alpine
volumes:
- redis-data:/data
networks:
- app-network
restart: unless-stopped
nginx:
image: nginx:alpine
ports:
- "80:80"
- "443:443"
volumes:
- ./nginx.conf:/etc/nginx/nginx.conf
- ./ssl:/etc/nginx/ssl
depends_on:
- nuxt
networks:
- app-network
restart: unless-stopped
networks:
app-network:
driver: bridge
volumes:
postgres-data:
redis-data:
5.3 启动服务 #
bash
docker-compose up -d
5.4 查看日志 #
bash
docker-compose logs -f nuxt
5.5 停止服务 #
bash
docker-compose down
六、Nginx配置 #
6.1 反向代理 #
nginx.conf:
nginx
events {
worker_connections 1024;
}
http {
upstream nuxt {
server nuxt:3000;
}
server {
listen 80;
server_name example.com;
location / {
proxy_pass http://nuxt;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_cache_bypass $http_upgrade;
}
}
}
6.2 HTTPS配置 #
nginx
server {
listen 443 ssl http2;
server_name example.com;
ssl_certificate /etc/nginx/ssl/cert.pem;
ssl_certificate_key /etc/nginx/ssl/key.pem;
location / {
proxy_pass http://nuxt;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
server {
listen 80;
server_name example.com;
return 301 https://$server_name$request_uri;
}
七、CI/CD集成 #
7.1 GitHub Actions #
.github/workflows/docker.yml:
yaml
name: Docker Build and Push
on:
push:
branches: [main]
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3
- name: Login to Docker Hub
uses: docker/login-action@v3
with:
username: ${{ secrets.DOCKER_USERNAME }}
password: ${{ secrets.DOCKER_PASSWORD }}
- name: Build and push
uses: docker/build-push-action@v5
with:
context: .
push: true
tags: ${{ secrets.DOCKER_USERNAME }}/my-nuxt-app:latest
7.2 GitLab CI #
.gitlab-ci.yml:
yaml
stages:
- build
- deploy
build:
stage: build
image: docker:latest
services:
- docker:dind
script:
- docker login -u $DOCKER_USERNAME -p $DOCKER_PASSWORD
- docker build -t $DOCKER_USERNAME/my-nuxt-app:$CI_COMMIT_SHA .
- docker push $DOCKER_USERNAME/my-nuxt-app:$CI_COMMIT_SHA
deploy:
stage: deploy
image: docker:latest
script:
- docker pull $DOCKER_USERNAME/my-nuxt-app:$CI_COMMIT_SHA
- docker-compose up -d
八、最佳实践 #
8.1 镜像优化 #
- 使用 Alpine 基础镜像
- 多阶段构建减小镜像大小
- 缓存依赖层
8.2 安全配置 #
- 使用非 root 用户运行
- 不在镜像中存储敏感信息
- 定期更新基础镜像
8.3 健康检查 #
dockerfile
HEALTHCHECK --interval=30s --timeout=10s --start-period=5s --retries=3 \
CMD curl -f http://localhost:3000/api/health || exit 1
九、总结 #
本章介绍了 Nuxt.js Docker 部署:
- Dockerfile 编写
- 多阶段构建优化
- Docker Compose 配置
- Nginx 反向代理
- CI/CD 集成
- 最佳实践
Docker 部署适合需要完全控制部署环境的场景,下一章我们将学习环境变量配置。
最后更新:2026-03-28