如何使用 GitHub Action 发布 Docker 镜像

前一阵子,我想在 Mathcheap 上实现 LaTeX 导出到 DOCX 格式的功能,一直没有找到合适的 JS 库去实现。目前可以很好实现这个功能的是 Pandoc , 美中不足的是 Pandoc 是 haskell 语言开发的,无法在 Node 环境和边缘服务器中运行。为了克服这个限制,我将 Pandoc 编译为 Webassembly。上周,我开源了 pandoc-wasm 这个编译流程,通过 Docker 镜像发布在 Docker Hub 上。在这个过程中,我探索了如何利用 GitHub Actions 自动构建和发布 Docker 镜像,极大地提升了开源项目的集成和部署效率。

为什么需要自动发布 Docker 镜像?

在尝试将 Pandoc 运行环境迁移到 Node 服务器的过程中,我试着构建了一套可靠的 pandoc-wasm 编译流程。因为 Mathcheap 依赖这套编译流程打包的产物,我打算开源并长期升级维护。Docker 是实现这一目标的绝佳工具,它可以将应用及其所有依赖打包到一个标准化的容器中。但每次手动构建镜像、打标签、然后推送到 Docker Hub 的过程,不仅繁琐,而且容易出错。尤其是在一个频繁迭代的开源项目中,自动化这一流程显得至关重要。这不仅能节省时间,还能确保每次代码合并后都能生成一个可靠的镜像。GitHub Actions 正是实现这一目标的利器。

准备工作

在开始之前,请确保你已经准备好以下几样东西:

  1. GitHub 仓库
  2. Docker Hub 账号
  3. Dockerfile 文件

Dockerfile 是一个文本文档,包含了一系列用户可以调用来组装镜像的指令。

第一步:配置 Docker Hub 访问凭证

为了让 GitHub Actions 能够登录你的 Docker Hub 账号并推送镜像,你需要将用户名和访问令牌(Access Token)安全地存储在 GitHub 中。

  1. 生成 Docker Hub 访问令牌

    • 登录 Docker Hub。
    • 进入 "Settings" -> "Personal access tokens"。
    • 点击 "Generate new token",创建一个具有读写删权限的令牌,并立即复制它
  2. 在 GitHub 仓库中设置 Secrets

    • 进入你的 GitHub 仓库,点击 "Settings" -> "Secrets and variables" -> "Actions"。
    • 点击 "New repository secret",创建两个新的 Secret:
      • DOCKERHUB_USERNAME: 你的 Docker Hub 用户名。
      • DOCKERHUB_TOKEN: 你刚刚生成的访问令牌。

通过这种方式,我们可以在工作流程中安全地使用这些凭证,而无需将它们硬编码到代码中。

第二步:创建 GitHub Actions 工作流程

接下来,在项目中创建一个 YAML 文件来定义自动化工作流程。

  1. 在仓库根目录下,创建 .github/workflows/ 文件夹。
  2. 在该文件夹下,创建一个新的 YAML 文件,例如 docker-publish.yml
yaml 复制代码
name: Build and Publish Docker image

on:
  push:
    tags:
      - "v*"
  workflow_dispatch:

env:
  IMAGE_NAME: ${{ secrets.DOCKERHUB_USERNAME }}/${{ github.event.repository.name }}

jobs:
  build-and-push:
    runs-on: ubuntu-latest

    steps:
      - name: Checkout code
        uses: actions/checkout@v4

      - name: Login to Docker Hub
        uses: docker/login-action@v3
        with:
          username: ${{ secrets.DOCKERHUB_USERNAME }}
          password: ${{ secrets.DOCKERHUB_TOKEN }}

      - name: Build and push Docker image
        uses: docker/build-push-action@v5
        with:
          context: ./docker
          file: ./docker/Dockerfile
          push: true
          tags: |
            ${{ env.IMAGE_NAME }}:${{ github.ref_name }}
            ${{ env.IMAGE_NAME }}:latest

      - name: Update Docker Hub description
        uses: peter-evans/dockerhub-description@v4
        with:
          username: ${{ secrets.DOCKERHUB_USERNAME }}
          password: ${{ secrets.DOCKERHUB_TOKEN }}
          repository: ${{ env.IMAGE_NAME }}
          short-description: ${{ github.event.repository.description }}
          readme-filepath: ./docker/README.md

解读工作流程文件

分解一下这个 YAML 文件的关键部分:

  • 触发条件 on:
    • push.tags: 以 v 开头的标签(例如 v1.0.0)。这能把镜像版本与项目版本对齐。
    • workflow_dispatch: 支持从 GitHub UI 手动触发。
  • env.IMAGE_NAME: 最终镜像名是 shenlu89/pandoc-wasmshenlu89 是我在 Docker Hub 的用户名,DOCKERHUB_USERNAME,仓库名来自当前 GitHub 仓库的名字。
  • docker/build-push-action@v5:
    • context: 指向 ./docker 目录与其中的 Dockerfile。
    • push: true 表示构建完成后会推送到远程。
    • tags: 同时推版本标签和 latest
  • peter-evans/dockerhub-description@v4:
    • 用仓库的简介和 ./docker/README.md 自动更新 Docker Hub 页面描述。

提交代码触发 GitHub Actions

推送标签触发发布

  • 创建并推送一个符合规则的版本标签,例如 v1.0.0:
bash 复制代码
git add . && git commit -m 'feat: xxx' 
git tag v1.0.0
git push origin v1.0.0
  • 或者在 GitHub 的 Actions 页面手动点击"Run workflow"。

最后,触发 GitHub Actions 工作流,自动完成镜像构建和推送 Docker Hub。

相关推荐
深蓝电商API5 小时前
爬虫+Docker:让你的爬虫项目一键部署、可移植
爬虫·docker·容器
ajassi20006 小时前
开源 Linux 服务器与中间件(七)数据库--MySQL
linux·服务器·数据库·ubuntu·开源
xiaohe06016 小时前
🔒 JavaScript 不是单线程吗?怎么还能上“锁”?!
javascript·github
ZHE|张恒6 小时前
使用 Docker 容器测试端口开放性
运维·docker·容器
切糕师学AI7 小时前
云原生技术栈解析:宿主机、容器、Docker、Kubernetes 之间的区别于联系
docker·云原生·容器·kubernetes
全栈小58 小时前
【代码管理】在本地使用github和gitee之后,可能存在冲突,导致再次提交代码时提示Couldn‘t connect to server
gitee·github·代码管理工具
NocoBase8 小时前
11 个在 GitHub 上最受欢迎的开源无代码 AI 工具
低代码·ai·开源·github·无代码·ai agent·airtable·内部工具·app builder
java_logo9 小时前
Docker 部署 MinIO 全指南
运维·windows·mongodb·docker·容器
我狸才不是赔钱货9 小时前
DevOps:打破开发与运维之间的高墙
运维·vscode·docker·devops