Docker为CI/CD流程带来以下优势: - 环境一致性:确保开发、测试和生产环境一致 - 隔离性:每个构建在独立容器中运行,互不干扰 - 可重复性:相同的Docker镜像在任何地方运行结果相同 - 快速部署:镜像一旦构建完成,可以快速部署到任何环境
典型的Docker CI/CD流水线包含以下组件:
在所有相关机器上安装Docker Engine
# Ubuntu示例
sudo apt-get update
sudo apt-get install docker-ce docker-ce-cli containerd.io
可选:安装Docker Compose
sudo curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose
为你的应用创建Dockerfile,例如一个Node.js应用:
# 使用官方Node.js镜像作为基础
FROM node:14-alpine
# 设置工作目录
WORKDIR /app
# 复制package.json和package-lock.json
COPY package*.json ./
# 安装依赖
RUN npm install
# 复制应用源代码
COPY . .
# 构建应用
RUN npm run build
# 暴露端口
EXPOSE 3000
# 定义启动命令
CMD ["npm", "start"]
name: Docker CI/CD
on:
push:
branches: [ main ]
pull_request:
branches: [ main ]
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Login to Docker Hub
uses: docker/login-action@v1
with:
username: ${{ secrets.DOCKER_HUB_USERNAME }}
password: ${{ secrets.DOCKER_HUB_TOKEN }}
- name: Build and push
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: yourusername/yourimage:latest
pipeline {
agent any
environment {
DOCKER_REGISTRY = "your-registry.com"
IMAGE_NAME = "your-image"
}
stages {
stage('Build') {
steps {
script {
docker.build("${DOCKER_REGISTRY}/${IMAGE_NAME}:${env.BUILD_NUMBER}")
}
}
}
stage('Test') {
steps {
script {
docker.image("${DOCKER_REGISTRY}/${IMAGE_NAME}:${env.BUILD_NUMBER}").inside {
sh 'npm test'
}
}
}
}
stage('Push') {
steps {
script {
docker.withRegistry('https://your-registry.com', 'registry-credentials') {
docker.image("${DOCKER_REGISTRY}/${IMAGE_NAME}:${env.BUILD_NUMBER}").push()
}
}
}
}
stage('Deploy') {
steps {
sshagent(['deploy-key']) {
sh "ssh user@server 'docker pull ${DOCKER_REGISTRY}/${IMAGE_NAME}:${env.BUILD_NUMBER} && docker-compose up -d'"
}
}
}
}
}
# 拉取最新镜像
docker pull yourusername/yourimage:latest
# 停止并移除旧容器
docker stop your-container || true && docker rm your-container || true
# 运行新容器
docker run -d --name your-container -p 80:3000 yourusername/yourimage:latest
创建docker-compose.yml
:
version: '3'
services:
web:
image: yourusername/yourimage:latest
ports:
- "80:3000"
restart: always
部署命令:
docker-compose pull
docker-compose up -d
使用多阶段构建:减少最终镜像大小
FROM node:14 as builder
WORKDIR /app
COPY . .
RUN npm install && npm run build
FROM nginx:alpine
COPY --from=builder /app/build /usr/share/nginx/html
不要使用latest标签:在生产中使用特定版本标签
扫描镜像安全漏洞:使用工具如Trivy、Clair
限制资源使用:
docker run -d --name myapp --memory=512m --cpus=1 myimage
使用.dockerignore文件:避免将不必要的文件复制到镜像中
集中化日志管理:使用ELK栈或类似方案
健康检查:
HEALTHCHECK --interval=30s --timeout=3s \
CMD curl -f http://localhost/ || exit 1
自动重启:
docker run --restart unless-stopped -d myimage
日志轮转:
docker run --log-opt max-size=10m --log-opt max-file=3 myimage
使用Kubernetes进行编排:
服务网格集成:
无服务器部署:
通过以上步骤和最佳实践,你可以建立一个高效、可靠的基于Docker的CI/CD流水线,实现从代码提交到生产部署的自动化流程。