Skip to content

Docker 安全实践

构建安全的容器化应用

安全最佳实践

1. 使用非 root 用户

dockerfile
# ❌ 以 root 用户运行(危险)
FROM node:18-alpine
WORKDIR /app
COPY . .
RUN npm ci
CMD ["node", "server.js"]

# ✅ 创建专用用户
FROM node:18-alpine
WORKDIR /app

# 创建用户和组
RUN addgroup -g 1001 -S nodejs && \
    adduser -S nextjs -u 1001 -G nodejs

# 复制文件并设置权限
COPY --chown=nextjs:nodejs package*.json ./
COPY --chown=nextjs:nodejs . .

# 切换用户
USER nextjs

CMD ["node", "server.js"]

2. 避免敏感信息泄露

dockerfile
# ❌ 敏感信息在镜像中
ENV DATABASE_PASSWORD=secret123
COPY . .

# ✅ 使用构建时 ARG(不进入最终镜像)
ARG BUILD_SECRET
RUN echo $BUILD_SECRET > /tmp/secret && rm /tmp/secret

# ✅ 生产环境通过环境变量注入
# docker run -e DB_PASSWORD=xxx myapp

3. 使用特定版本而非 latest

dockerfile
# ❌ latest 标签可能导致不可预测的构建
FROM node:latest

# ✅ 固定版本,确保可复现
FROM node:18.19.1-alpine

4. 最小化镜像层数

dockerfile
# ✅ 合并指令
RUN apt-get update && \
    apt-get install -y --no-install-recommends \
        curl \
        vim \
    && rm -rf /var/lib/apt/lists/*

5. 使用健康检查

dockerfile
HEALTHCHECK --interval=30s --timeout=3s \
    CMD node -e "require('http').get('http://localhost:3000/health', (r) => process.exit(r.statusCode === 200 ? 0 : 1))"

安全扫描工具

Trivy 扫描

bash
# 安装
brew install trivy

# 扫描镜像
trivy image myapp:latest

# 扫描文件系统
trivy fs .

# 扫描漏洞报告
trivy image --format json --output result.json myapp:latest

Docker Scout

bash
# 登录
docker scout login

# 分析镜像
docker scout cves myapp:latest

# 推荐修复
docker scout recommendations myapp:latest

Docker Bench Security

bash
# 运行安全检查
docker run -it --rm \
    --net host \
    --pid host \
    --userns host \
    -v /var/lib/docker:/var/lib/docker \
    aquasec/docker-bench-security:latest

安全加固检查清单

检查项说明
非 root 用户容器不以 root 运行
最小权限只授予必要权限
镜像签名使用 Docker Content Trust
漏洞扫描定期扫描镜像漏洞
只读根文件系统使用 --read-only
资源限制设置 CPU/内存限制
敏感信息不在镜像中存储密钥
及时更新定期更新基础镜像

运行时安全

bash
# 资源限制
docker run \
    --memory=512m \
    --cpus=0.5 \
    --read-only \
    --tmpfs /tmp:size=10m,mode=1777 \
    myapp

# 安全选项
docker run \
    --security-opt=no-new-privileges \
    --cap-drop ALL \
    --cap-add NET_BIND_SERVICE \
    myapp

面试高频题

Q1: 如何确保容器以非 root 用户运行?

答案:

  1. 在 Dockerfile 中创建专用用户
  2. 使用 USER 指令切换用户
  3. 设置文件所有权
dockerfile
RUN adduser -S appuser
COPY --chown=appuser:appuser . .
USER appuser

Q2: 如何防止敏感信息泄露?

答案:

  1. 不在 Dockerfile 中硬编码密钥
  2. 使用 .dockerignore 排除敏感文件
  3. 通过环境变量或密钥管理服务注入
  4. 构建时不使用 --build-arg 传递敏感信息

Q3: Docker 容器有哪些安全风险?

答案:

  • 容器逃逸风险
  • 权限过大(privileged 模式)
  • 敏感信息泄露
  • 镜像漏洞
  • 网络隔离不足
  • 资源未限制

前端面试知识库