Files
cs-note/hzh/MS/05-部署运维/01-容器化.md
T
2026-05-24 11:42:38 +08:00

4.1 KiB
Raw Blame History

tags, create time
tags create time
microservice
docker
container
image-optimization
2026-05-05

容器化

概述

Docker 容器是微服务交付的标准单元。它解决了"在我机器上是好的"这个经典问题——开发、测试、生产使用完全一致的运行时环境。

graph TB
    CODE["源代码"] --> BUILD["CI 构建镜像"]
    BUILD --> REGISTRY["镜像仓库<br/>Harbor / ECR / ACR"]
    REGISTRY --> K8s["Kubernetes 部署"]
    
    style BUILD fill:#e3f2fd
    style REGISTRY fill:#fff3e0
    style K8s fill:#e8f5e9

Dockerfile 最佳实践

Go 多阶段构建(推荐)

# ========== 阶段 1: 构建 ==========
FROM golang:1.22-alpine AS builder

RUN apk --no-cache add git ca-certificates

WORKDIR /app
COPY go.mod go.sum ./
RUN go mod download

COPY . .
ARG LDFLAGS="-s -w -extldflags '-static'"
RUN CGO_ENABLED=0 GOOS=linux go build -ldflags "$LDFLAGS" -o server .

# ========== 阶段 2: 运行时 ==========
FROM alpine:latest

RUN apk --no-cache add ca-certificates tzdata && \
    cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime && \
    echo "Asia/Shanghai" > /etc/timezone

RUN addgroup -S appgroup && adduser -S appuser -G appgroup
USER appuser

WORKDIR /app
COPY --from=builder /app/server .

EXPOSE 8080

HEALTHCHECK --interval=30s --timeout=3s --start-period=5s --retries=3 \
    CMD wget -qO- http://localhost:8080/healthz || exit 1

CMD ["./server"]

关键优化点

优化项 方法 效果
多阶段构建 编译和运行分离 镜像从 800MB → 15MB
alpine 基础镜像 替代 debian/ubuntu 减小体积
非 root 运行 USER appuser 安全合规
静态链接 CGO_ENABLED=0 不依赖系统库
layer cache go.mod 先 COPY CI 加速构建
健康检查 HEALTHCHECK 指令 K8s 原生支持

.dockerignore

.git
.gitignore
*.md
vendor/
tests/
*.log
.DS_Store
.idea/
.vscode/

[!tip] 为什么 .dockerignore 很重要?

如果不排除 .git 目录,整个版本历史都会被打包进镜像(增加数百 MB)。如果排除不当,可能遗漏必要的配置文件。

镜像安全

flowchart LR
    Scan["镜像扫描 (Trivy/Snyk)"] --> Clean{"漏洞等级?"}
    
    Clean -- "CRITICAL/HIGH" --> Block["❌ 阻止推送"]
    Clean -- "MEDIUM" --> Review["⚠️ 人工审核"]
    Clean -- "LOW/INFO" --> Allow["✅ 允许推送"]
    
    style Block fill:#ffebee
    style Review fill:#fff3e0
    style Allow fill:#e8f5e9

安全检查清单

  • 不使用 latest tag(永远用具体版本号)
  • 不安装不必要的软件包(apk del --purge .build-deps)
  • 定期更新基础镜像(修复 CVE)
  • 使用非 root 用户运行
  • 镜像不包含密钥、密码、私钥
  • 使用最小基础镜像(scratch / distroless)

Distroless 镜像

Google 推出的无 shell、无包管理器的极简运行时镜像:

# 最极致的精简
FROM gcr.io/distroless/static-debian12
COPY --from=builder /app/server .
USER nonroot
CMD ["./server"]

⚠️ 注意:distroless 镜像没有 shell (/bin/sh),调试时需要额外工具(如 debug 镜像或 kubectl exec 到 sidecar)。

镜像仓库管理

flowchart LR
    Dev["开发者本地"] -->|"docker push"| DEV_REPO["dev 仓库<br/>v1.2.3-dev"]
    
    Staging["Staging 验证"] -->|"通过"| PROD_REPO["prod 仓库<br/>v1.2.3"]
    
    K8s["K8s Cluster"] -->|"pull"| PROD_REPO
    
    PR["PR Merge"] --> Tag["打标签 v1.2.3"]
    Tag --> ProdRepoMove["移动到 prod 仓库"]
    
    style DEV_REPO fill:#fff3e0
    style PROD_REPO fill:#e8f5e9
仓库方案 特点 适用场景
Harbor 自托管,RBAC + 扫描 国内企业首选
ECR / ACR / GCR 云厂商托管 全云环境
Docker Hub 公共免费 开源项目

关联笔记