当前位置: 首页 > news >正文

Docker 实战教程(7) | 镜像管理和仓库操作

前边篇章我们已经介绍了

  1. Docker 基础概念和安装
  2. Docker 常用命令实践
  3. Docker 网络机制详解
  4. Docker 数据卷和挂载
  5. Dockerfile 编写和镜像构建
  6. Docker Compose 多容器编排

本篇为系列最后一章,介绍 Docker 的镜像管理和仓库操作。

本教程侧重于命令实践和理解,提供可在本地环境测试的实例,每章结束都有总结要点。

7.1 Docker 镜像管理基础

我们之前介绍过一期自建镜像站的若干方案: Docker 管理 | 代理配置、内网共享和 Harbor 部署。

本篇侧重展开介绍 docker 镜像相关的概念,以及原生支持的镜像站方案。

镜像的生命周期

# 镜像生命周期概览
构建 -> 标记 -> 推送 -> 拉取 -> 运行 -> 删除# 查看本地镜像
docker images
docker image ls# 查看镜像详细信息
docker image inspect nginx:alpine# 查看镜像历史
docker image history nginx:alpine# 查看镜像大小
docker images --format "table {{.Repository}}\t{{.Tag}}\t{{.Size}}"

镜像标记和命名

# 镜像命名规范
[registry_host[:port]/]username/repository[:tag]# 示例
docker.io/library/nginx:latest          # 官方镜像,前缀 docker.io/library/ 可以省略
docker.io/username/myapp:v1.0           # 用户镜像,前缀 docker.io/ 可以省略
registry.example.com/team/app:latest    # 私有仓库镜像# 为镜像添加标记
docker tag nginx:alpine myregistry.com/nginx:v1.0
docker tag myapp:latest myapp:v1.0
docker tag myapp:latest myapp:production# 查看同一镜像的多个标记,需匹配到 username/repository
docker images myapp

镜像清理和优化

# 删除单个镜像
docker rmi nginx:alpine
docker image rm nginx:alpine# 删除多个镜像
docker rmi $(docker images -q ubuntu)# 删除悬空镜像(dangling images)
docker image prune# 删除所有未使用的镜像
docker image prune -a# 删除指定时间前的镜像
docker image prune -a --filter "until=24h"# 查看镜像占用空间
docker system df# 全面清理系统
docker system prune -a --volumes

7.2 Docker Hub 操作

Docker Hub 基本操作

# 登录 Docker Hub
docker login # -u username -p password# 登录指定仓库
docker login registry.example.com# 查看登录状态
cat ~/.docker/config.json

注意,这里用户名的大小写敏感。一般地,建议在设置页面创建 token,通过 token 登录。

# 搜索镜像
docker search nginx
docker search --limit 5 --filter stars=100 nginx# 拉取镜像
docker pull nginx
docker pull nginx:1.21-alpine
docker pull ubuntu:20.04# 推送镜像到 Docker Hub
# 1. 构建镜像
docker build -t username/myapp:v1.0 .# 2. 推送镜像
docker push username/myapp:v1.0# 登出
docker logout

上边命令中的 push 镜像,以及 pull 私人镜像需要登录。

实践:发布自己的镜像

# 创建示例应用
mkdir -p /tmp/docker-tutorial/my-web-app
cd /tmp/docker-tutorial/my-web-app# 创建简单的 Web 应用
cat > app.py << 'EOF'
from flask import Flask, jsonify
import os
import socketapp = Flask(__name__)@app.route('/')
def hello():return jsonify({'message': 'Hello from my Docker app!','hostname': socket.gethostname(),'version': os.environ.get('APP_VERSION', '1.0.0')})@app.route('/health')
def health():return jsonify({'status': 'healthy'})if __name__ == '__main__':app.run(host='0.0.0.0', port=5000)
EOF# 创建 requirements.txt
cat > requirements.txt << 'EOF'
Flask==2.3.3
EOF# 创建 Dockerfile
cat > Dockerfile << 'EOF'
FROM python:3.11-alpineWORKDIR /appCOPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txtCOPY app.py .EXPOSE 5000ENV APP_VERSION=1.0.0CMD ["python", "app.py"]
EOF# 构建镜像(替换 username 为你的 Docker Hub 用户名)
docker build -t username/my-web-app:1.0.0 .
docker build -t username/my-web-app:latest .# 测试镜像
docker run -d -p 5000:5000 --name test-app username/my-web-app:1.0.0# 测试应用
curl http://localhost:5000
curl http://localhost:5000/health# 停止测试容器
docker stop test-app
docker rm test-app# 推送到 Docker Hub(需要先登录)
# docker login
# docker push username/my-web-app:1.0.0
# docker push username/my-web-app:latest

7.3 私有镜像仓库

搭建本地 Registry

关于镜像站,我们之前详细讲过一期,可以参考 『{%post_link server/docker/docker-registry }』。

这里仅介绍自带 Registry 的方法。

# 启动本地 Registry
docker run -d \-p 5000:5000 \--restart=always \--name registry \-v registry_data:/var/lib/registry \registry:2# 验证 Registry 运行状态
curl http://localhost:5000/v2/# 配置 Docker 信任本地仓库(仅用于测试)
# 编辑 /etc/docker/daemon.json (Linux) 或 Docker Desktop 设置
{"insecure-registries": ["localhost:5000"]
}# 重启 Docker 服务
# sudo systemctl restart docker  # Linux
# 或重启 Docker Desktop# 推送镜像到本地仓库
docker tag username/my-web-app:1.0.0 localhost:5000/my-web-app:1.0.0
docker push localhost:5000/my-web-app:1.0.0# 从本地仓库拉取镜像
docker pull localhost:5000/my-web-app:1.0.0# 查看仓库中的镜像
curl http://localhost:5000/v2/_catalog
curl http://localhost:5000/v2/my-web-app/tags/list

带认证的私有仓库

# 创建认证配置目录
mkdir -p /tmp/docker-tutorial/registry-auth
cd /tmp/docker-tutorial/registry-auth# 创建用户认证文件
mkdir auth
docker run --rm \--entrypoint htpasswd \httpd:2 -Bbn testuser testpass > auth/htpasswd# 创建 SSL 证书(自签名,仅用于测试)
mkdir certs
openssl req -newkey rsa:4096 -nodes -sha256 \-keyout certs/domain.key -x509 -days 365 \-out certs/domain.crt \-subj "/C=CN/ST=Beijing/L=Beijing/O=Test/CN=localhost"# 启动带认证的 Registry
docker run -d \-p 5443:5000 \--restart=always \--name secure-registry \-v $(pwd)/auth:/auth \-v $(pwd)/certs:/certs \-v registry_secure_data:/var/lib/registry \-e "REGISTRY_AUTH=htpasswd" \-e "REGISTRY_AUTH_HTPASSWD_REALM=Registry Realm" \-e "REGISTRY_AUTH_HTPASSWD_PATH=/auth/htpasswd" \-e "REGISTRY_HTTP_TLS_CERTIFICATE=/certs/domain.crt" \-e "REGISTRY_HTTP_TLS_KEY=/certs/domain.key" \registry:2# 登录到私有仓库
docker login localhost:5443
# 用户名: testuser
# 密码: testpass# 推送镜像到私有仓库
docker tag username/my-web-app:1.0.0 localhost:5443/my-web-app:1.0.0
docker push localhost:5443/my-web-app:1.0.0# 清理
docker stop registry secure-registry
docker rm registry secure-registry

使用 Docker Compose 搭建完整的私有仓库

可以通过 config.yml + docker-compose.yml 搭建完整的私有仓库。

# 创建私有仓库项目
mkdir -p /tmp/docker-tutorial/private-registry
cd /tmp/docker-tutorial/private-registry# 创建目录结构
mkdir -p auth certs data# 创建用户认证文件
docker run --rm \--entrypoint htpasswd \httpd:2 -Bbn admin adminpass > auth/htpasswd# 创建 Registry 配置
cat > config.yml << 'EOF'
version: 0.1
log:fields:service: registry
storage:cache:blobdescriptor: inmemoryfilesystem:rootdirectory: /var/lib/registry
http:addr: :5000headers:X-Content-Type-Options: [nosniff]
health:storagedriver:enabled: trueinterval: 10sthreshold: 3
EOF# 创建 docker-compose.yml
cat > docker-compose.yml << 'EOF'
version: '3.8'services:registry:image: registry:2ports:- "5000:5000"environment:REGISTRY_AUTH: htpasswdREGISTRY_AUTH_HTPASSWD_REALM: Registry RealmREGISTRY_AUTH_HTPASSWD_PATH: /auth/htpasswdREGISTRY_STORAGE_FILESYSTEM_ROOTDIRECTORY: /datavolumes:- ./auth:/auth- ./data:/data- ./config.yml:/etc/docker/registry/config.ymlrestart: unless-stoppednetworks:- registry-networkregistry-ui:image: joxit/docker-registry-ui:latestports:- "8080:80"environment:REGISTRY_TITLE: Private Docker RegistryREGISTRY_URL: http://registry:5000DELETE_IMAGES: trueSHOW_CONTENT_DIGEST: truedepends_on:- registrynetworks:- registry-networknetworks:registry-network:driver: bridgevolumes:registry-data:
EOF# 启动私有仓库
docker-compose up -d# 查看服务状态
docker-compose ps# 登录私有仓库
docker login localhost:5000
# 用户名: admin
# 密码: adminpass# 推送镜像
docker tag username/my-web-app:1.0.0 localhost:5000/my-web-app:1.0.0
docker push localhost:5000/my-web-app:1.0.0# 访问 Web UI
echo "访问 http://localhost:8080 查看仓库 UI"# 清理
docker-compose down -v

7.4 镜像安全和最佳实践

镜像安全扫描

# 使用 Docker Scout 扫描镜像(需要 Docker Desktop)
docker scout cves nginx:latest# 使用 Trivy 扫描镜像
# 安装 Trivy
brew install trivy  # macOS
# 或
curl -sfL https://raw.githubusercontent.com/aquasecurity/trivy/main/contrib/install.sh | sh -s -- -b /usr/local/bin# 扫描镜像漏洞
trivy image nginx:latest
trivy image --severity HIGH,CRITICAL nginx:latest# 扫描本地镜像
trivy image username/my-web-app:1.0.0# 生成报告
trivy image --format json --output report.json nginx:latest

镜像签名和验证

# 启用 Docker Content Trust
export DOCKER_CONTENT_TRUST=1# 生成签名密钥
docker trust key generate mykey# 为仓库添加签名者
docker trust signer add --key mykey.pub myuser username/myapp# 推送签名镜像
docker push username/myapp:signed# 验证镜像签名
docker trust inspect username/myapp:signed# 禁用 Content Trust
export DOCKER_CONTENT_TRUST=0

镜像优化最佳实践

创建优化示例

mkdir -p /tmp/docker-tutorial/image-optimization
cd /tmp/docker-tutorial/image-optimization

创建未优化的 Dockerfile.bad 文件:

cat > Dockerfile.bad << 'EOF'
FROM ubuntu:20.04RUN apt-get update
RUN apt-get install -y python3
RUN apt-get install -y python3-pip
RUN apt-get install -y curl
RUN apt-get install -y vimCOPY . /app
WORKDIR /appRUN pip3 install flask
RUN pip3 install requestsEXPOSE 5000CMD ["python3", "app.py"]
EOF

创建优化的 Dockerfile.good 文件:

cat > Dockerfile.good << 'EOF'
# 使用更小的基础镜像
FROM python:3.11-alpine# 设置工作目录
WORKDIR /app# 只复制需要的文件
COPY requirements.txt .# 合并 RUN 指令,清理缓存
RUN pip install --no-cache-dir -r requirements.txt# 复制应用代码
COPY app.py .# 创建非 root 用户
RUN addgroup -g 1001 -S appgroup && \adduser -u 1001 -S appuser -G appgroup# 切换到非 root 用户
USER appuserEXPOSE 5000# 使用 exec 形式的 CMD
CMD ["python", "app.py"]
EOF

创建其他文件:

# 创建 .dockerignore 文件
cat > .dockerignore << 'EOF'
.git
.gitignore
README.md
Dockerfile*
.dockerignore
node_modules
npm-debug.log
coverage/
.nyc_output
*.log
.DS_Store
EOF# 创建应用文件
cat > app.py << 'EOF'
from flask import Flask
app = Flask(__name__)@app.route('/')
def hello():return 'Hello from optimized Docker image!'if __name__ == '__main__':app.run(host='0.0.0.0', port=5000)
EOFcat > requirements.txt << 'EOF'
Flask==2.3.3
EOF
# 构建并比较镜像大小
docker build -f Dockerfile.bad -t myapp:bad .
docker build -f Dockerfile.good -t myapp:good .# 比较镜像大小
docker images | grep myapp# 分析镜像层
docker history myapp:bad
docker history myapp:good

7.5 多架构镜像构建

使用 buildx 构建多架构镜像

# 启用 buildx
docker buildx version# 创建新的构建器
docker buildx create --name multiarch --driver docker-container --use
docker buildx inspect --bootstrap# 查看支持的平台
docker buildx ls# 构建多架构镜像
mkdir -p /tmp/docker-tutorial/multiarch
cd /tmp/docker-tutorial/multiarchcat > Dockerfile << 'EOF'
FROM --platform=$BUILDPLATFORM golang:1.21-alpine AS builderARG TARGETPLATFORM
ARG BUILDPLATFORM
ARG TARGETOS
ARG TARGETARCHWORKDIR /app
COPY main.go .RUN CGO_ENABLED=0 GOOS=${TARGETOS} GOARCH=${TARGETARCH} go build -o app main.goFROM alpine:latest
RUN apk --no-cache add ca-certificates
WORKDIR /root/
COPY --from=builder /app/app .
EXPOSE 8080
CMD ["./app"]
EOFcat > main.go << 'EOF'
package mainimport ("fmt""net/http""runtime"
)func handler(w http.ResponseWriter, r *http.Request) {fmt.Fprintf(w, "Hello from %s/%s!", runtime.GOOS, runtime.GOARCH)
}func main() {http.HandleFunc("/", handler)fmt.Println("Server starting on :8080")http.ListenAndServe(":8080", nil)
}
EOF# 构建多架构镜像并推送
docker buildx build \--platform linux/amd64,linux/arm64,linux/arm/v7 \-t username/multiarch-app:latest \--push .# 查看镜像清单
docker buildx imagetools inspect username/multiarch-app:latest

7.6 镜像仓库集成和 CI/CD

GitHub Actions 集成

更一般地模板可以从高星项目(比如 Open-WebUI, One-API 等)中摘取参考。

# .github/workflows/docker.yml
name: Build and Push Docker Imageon:push:branches: [ main ]tags: [ 'v*' ]pull_request:branches: [ main ]env:REGISTRY: docker.ioIMAGE_NAME: username/myappjobs:build:runs-on: ubuntu-latestpermissions:contents: readpackages: writesteps:- name: Checkout repositoryuses: actions/checkout@v4- name: Set up Docker Buildxuses: docker/setup-buildx-action@v3- name: Log in to Docker Hubif: github.event_name != 'pull_request'uses: docker/login-action@v3with:registry: ${{ env.REGISTRY }}username: ${{ secrets.DOCKER_USERNAME }}password: ${{ secrets.DOCKER_PASSWORD }}- name: Extract metadataid: metauses: docker/metadata-action@v5with:images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}tags: |type=ref,event=branchtype=ref,event=prtype=semver,pattern={{version}}type=semver,pattern={{major}}.{{minor}}- name: Build and push Docker imageuses: docker/build-push-action@v5with:context: .platforms: linux/amd64,linux/arm64push: ${{ github.event_name != 'pull_request' }}tags: ${{ steps.meta.outputs.tags }}labels: ${{ steps.meta.outputs.labels }}cache-from: type=ghacache-to: type=gha,mode=max

镜像版本管理策略

# 语义化版本标记
docker tag myapp:latest myapp:1.0.0
docker tag myapp:latest myapp:1.0
docker tag myapp:latest myapp:1# 基于 Git 提交的标记
GIT_COMMIT=$(git rev-parse --short HEAD)
docker tag myapp:latest myapp:${GIT_COMMIT}# 基于构建时间的标记
BUILD_DATE=$(date +%Y%m%d-%H%M%S)
docker tag myapp:latest myapp:${BUILD_DATE}# 环境特定标记
docker tag myapp:latest myapp:dev
docker tag myapp:latest myapp:staging
docker tag myapp:latest myapp:production

本章总结

在本章中,我们深入学习了 Docker 镜像管理和仓库操作:

  1. 镜像管理基础:掌握了镜像的生命周期、命名规范和清理优化
  2. Docker Hub 操作:学会了镜像的搜索、拉取、推送和发布流程
  3. 私有仓库搭建:实践了本地 Registry 和带认证的私有仓库部署
  4. 镜像安全:了解了安全扫描、签名验证和最佳实践
  5. 多架构构建:掌握了使用 buildx 构建跨平台镜像
  6. CI/CD 集成:学习了镜像构建的自动化和版本管理策略

安全考虑

  • 不在镜像中包含敏感信息
  • 使用非 root 用户运行应用
  • 定期更新基础镜像
  • 启用镜像签名和验证
  • 实施访问控制和审计

镜像优化技巧

  • 选择合适的基础镜像
  • 合并 RUN 指令减少层数
  • 使用 .dockerignore 排除不必要文件
  • 利用构建缓存提高构建速度
  • 实施多阶段构建分离构建和运行环境

至此,我们已经完成了 Docker 教程的所有核心章节。从基础概念到高级应用,涵盖了 Docker 的完整生态系统。这些知识将帮助你在实际项目中有效地使用 Docker 技术,构建、部署和管理容器化应用。

http://www.dtcms.com/a/453645.html

相关文章:

  • 百度快照抓取的是网站哪里的内容建站公司怎么接单
  • 江苏省建设工程竣工备案网站网站结构优化包括哪些
  • open manus实战:生成一个贪吃蛇游戏
  • 制作销售网站清浦网站建设
  • 建站为应用技术长沙有实力的关键词优化价格
  • 内网隧道突破:红队实战指南
  • 宿州北京网站建设保亭网站建设
  • Java-142 深入浅出 MySQL Spring事务失效的常见场景与解决方案详解(4)
  • 网站优化培训好学吗公司网站变更域名
  • 【开题答辩全过程】以 安全电子选举系统的设计与实现为例,包含答辩的问题和答案
  • ESP32项目(三、控制继电器,伺服电机,舵机)
  • Python 3 内置函数详解
  • Spring AI快速入门以及项目的创建
  • 微网站制作工具有哪些霞浦建设局总规网站
  • 免费微商城网站建设网站开发团队人员构成
  • 个人网页简单模板下载seo是怎么优化的
  • 杭州有实力的网站开发直接通过域名访问wordpress
  • 多目标识别YOLO :YOLOV3 原理
  • 【Qt】QSS
  • 反射还是代码生成?Go反射使用的边界与取舍|Go语言进阶(11)
  • 国际外贸网站建设前端自适应模板
  • 网站建设代码流程花店网站建设个人小结
  • 德阳建设公司网站网站制作里的更多怎么做
  • HandBrake:视频压缩工具
  • 建设部门的网站wordpress图片批量上传插件下载
  • 致远OA配置HTTPS访问避坑帖
  • 快速搭建网站视频wordpress托管在哪里
  • AssemblyScript 入门教程(5):深入理解 TypedArray
  • 【PCB电路设计】常见元器件简介(电阻、电容、电感、二极管、三极管以及场效应管)
  • STM32G474单片机开发入门(六)定时器TIMER详解及实战含源码