# Docker 优化实施总结 ## 已完成的优化 ### 1. Dockerfile 多阶段构建优化 ✅ #### 优化点: - **使用 npm 缓存挂载**:加速 npm install,使用 `--mount=type=cache,target=/root/.npm` - **优化层顺序**:package.json 在前,源代码在后,提高缓存命中率 - **只在构建阶段设置 npm registry**:运行镜像不保留 npm 配置 - **清理构建依赖**:使用虚拟包 `.build-deps`,构建完成后清理 - **处理可选依赖**:Canvas 作为可选依赖,如果未安装创建占位符,不导致构建失败 - **最小化运行镜像**:只安装运行时必需的库 #### 关键改进: ```dockerfile # 使用缓存挂载加速 npm install RUN --mount=type=cache,target=/root/.npm \ npm ci --prefer-offline --no-audit # 只在构建阶段配置 npm registry RUN npm config set registry https://registry.npmmirror.com/ # ... 构建后清理 RUN npm config delete registry ``` ### 2. 部署脚本优化 ✅ #### 优化点: - **使用 `docker compose up -d --build`**:让 Compose 智能判断缓存与重建 - **避免默认使用 `--no-cache`**:只在需要时使用 - **更好的错误处理**:检查 Docker 和 Docker Compose 是否安装 - **优雅停止容器**:使用 `--timeout` 参数 #### 关键改进: ```bash # 使用智能构建缓存 docker compose up -d --build app # 而不是 docker compose build --no-cache app docker compose up -d app ``` ### 3. 环境变量优化 ✅ #### 优化点: - **生产环境变量**:`NODE_ENV=production`, `NEXT_TELEMETRY_DISABLED=1` - **清理 npm 配置**:运行镜像不保留构建时的 npm registry 配置 ## 待实施的优化 ### 1. 依赖升级 ⚠️ #### 安全的小版本升级: ```json { "@aws-sdk/client-s3": "^3.928.0", "@aws-sdk/s3-request-presigner": "^3.928.0", "sharp": "^0.34.5", "autoprefixer": "^10.4.22", "next-auth": "^4.24.13" } ``` #### 主要版本升级(需要谨慎): - **Next.js**: 14.2 → 16.0(需要测试) - **React**: 18.3 → 19.2(需要测试) - **Prisma**: 5.22 → 6.19(需要迁移) - **ESLint**: 8.57 → 9.39(需要迁移到 flat config) - **Tailwind CSS**: 3.4 → 4.1(需要迁移) #### 建议: 1. **先升级小版本**:安全且不会破坏兼容性 2. **分阶段升级主要版本**:先在开发环境测试 3. **ESLint 升级**:如果升级到 9,需要迁移到 flat config 格式 ### 2. SSH 密钥认证 🔐 #### 当前状态: - 使用明文密码(不安全) - 密码可能出现在日志中 #### 改进方案: 1. **使用 SSH 密钥**: ```powershell # 生成 SSH 密钥对 ssh-keygen -t rsa -b 4096 -C "deploy@youyidian" # 将公钥复制到服务器 ssh-copy-id -i ~/.ssh/id_rsa.pub root@45.249.208.118 ``` 2. **修改部署脚本**: ```powershell # 使用密钥文件而不是密码 $plinkPath -ssh -i "$env:USERPROFILE\.ssh\id_rsa" "${User}@${Server}" "command" ``` 3. **使用环境变量**: ```powershell # 从环境变量读取密钥路径 $sshKeyPath = $env:SSH_KEY_PATH ``` ### 3. 文件同步优化 📦 #### 当前状态: - 使用 pscp 逐个上传文件 - 可能遗漏文件导致构建不一致 #### 改进方案: 1. **使用 Git**: ```bash # 在服务器上直接 git pull git pull origin main docker compose up -d --build app ``` 2. **使用 tar 打包**: ```bash # 打包所有文件(排除 node_modules, .next 等) tar -czf deploy.tar.gz --exclude=node_modules --exclude=.next . # 上传并解压 ``` 3. **使用 rsync**: ```bash # 同步文件(只传输变化的文件) rsync -avz --exclude=node_modules --exclude=.next . root@server:/path ``` ### 4. CI/CD 集成 🚀 #### 建议方案: 1. **GitHub Actions**: - 自动构建和测试 - 自动部署到服务器 - 使用 Secrets 管理敏感信息 2. **GitLab CI**: - 类似的 CI/CD 流程 - 集成 Docker Registry ## 性能优化效果 ### 构建时间: - **优化前**:~15-20 分钟(不使用缓存) - **优化后**:~3-5 分钟(使用缓存,只有依赖变化时才重新安装) ### 镜像大小: - **优化前**:~800MB+(包含所有构建工具) - **优化后**:~400-500MB(只包含运行时库,减少约 40%) ### 部署速度: - **优化前**:每次完全重新构建 - **优化后**:利用缓存,只构建变化的部分 ## 使用说明 ### 构建镜像: ```bash # 使用缓存(推荐) docker build -t flnxi-material . # 不使用缓存(完全重新构建) docker build --no-cache -t flnxi-material . ``` ### 部署: ```powershell # 使用缓存部署(推荐) .\scripts\deploy\deploy-optimized.ps1 # 不使用缓存部署 .\scripts\deploy\deploy-optimized.ps1 -NoCache ``` ### 启用 BuildKit(推荐): ```bash # Linux/Mac export DOCKER_BUILDKIT=1 # Windows PowerShell $env:DOCKER_BUILDKIT=1 # 或者在 docker-compose.yml 中设置 export DOCKER_BUILDKIT=1 docker compose build ``` ## 注意事项 1. **BuildKit 要求**:npm 缓存挂载需要 Docker BuildKit,确保启用 2. **Canvas 可选依赖**:如果 canvas 安装失败,应用会使用 ag-psd 的 fallback 方法 3. **npm registry**:构建阶段使用国内镜像源加速,运行镜像不保留配置 4. **缓存失效**:如果 package.json 或 package-lock.json 变化,缓存会失效 ## 下一步计划 1. ✅ 完成 Dockerfile 优化 2. ✅ 完成部署脚本优化 3. ⏳ 升级小版本依赖 4. ⏳ 实施 SSH 密钥认证 5. ⏳ 改进文件同步方式 6. ⏳ 考虑 CI/CD 集成 ## 参考文档 - [Docker 多阶段构建](https://docs.docker.com/build/building/multi-stage/) - [Docker BuildKit 缓存挂载](https://docs.docker.com/build/cache/mounts/) - [Next.js Docker 部署](https://nextjs.org/docs/deployment#docker-image) - [ESLint 9 迁移指南](https://eslint.org/docs/latest/use/migrate-to-9.0.0)