持续集成指南:GitHubAction 自动构建 + 部署 AspNetCore 项目
前言
之前研究了使用 GitHub Action 自动构建和发布 nuget 包:开发现代化的.NetCore控制台程序:(4)使用GithubAction自动构建以及发布nuget包
现在更进一步,使用 GitHub Action 在其提供的 runner 里构建 docker 镜像,之后提交到阿里云镜像私有仓库,再在本地的 runner 将镜像 pull 下来运行。
本文以 AIHub 项目为例。
AIHub 是一个集成多种模型的 AI 平台,提供了大模型、计算机视觉、自然语言处理等多种功能,基于 AspNetCore + Blazor Server 技术开发。
准备 Dockerfile
首先准备好构建镜像的 Dockerfile
一般来说使用 dotnet cli 创建项目的时候可以自动生成这个 Dockerfile
没有的话可以参考我这个
可以先在本地试一下 build 有没有问题
一切正常可以进入下一步
创建私有镜像仓库
可以自行搭建,也可以使用云服务产品,我这里使用阿里云的「容器镜像服务 ACR」,个人版是免费的。
创建一个镜像仓库,代码源选择「本地仓库」,可以通过命令行推送镜像到镜像仓库。
PS: 我看里面还有 GitHub 仓库作为代码源,不过我还没测试。
创建之后有个操作指南,这不是很重要,我们只需要关注用户名和密码就行。
用于登录的用户名为阿里云账号全名,密码为开通服务时设置的密码。
可以在访问凭证页面修改凭证密码。
OK,这些信息保存好,接下来需要用到。
本文使用的仓库地址是: registry.cn-hangzhou.aliyuncs.com/deali/aihub-test
配置 GitHub Action Secret
将阿里云仓库的地址、用户名、密码等信息配置到 Action Secret 中
这里我设置的名字是
ALIYUN_DOCKER_REPO
ALIYUN_USERNAME
ALIYUN_PWD
构建镜像
编写 GitHub workflow 配置,细节不再赘述,不清楚的同学可以参考这篇文章: 开发现代化的.NetCore控制台程序:(4)使用GithubAction自动构建以及发布nuget包
GitHub 提供的 workflow
这是 GitHub 提供的,我没有使用这个方案,有兴趣的同学可以自行尝试一下。
简单版 workflow
这是我自己写的 workflow 比 GitHub 提供的例子简单一些
这个 build 步骤,在 GitHub 托管的 runner 上构建 docker 镜像,并且推送到私有镜像仓库。
镜像的 tag 版本,我使用了 run_id
这个环境变量,代表本次构建任务的唯一 ID,例如 1658821493
也可以使用 ${{ github.sha }}
代表这次的 commit sha ,但我觉得太长了就没有使用
GITHUB_SHA
: 触发工作流的提交 SHA。 此提交 SHA 的值取决于触发工作流程的事件。 有关详细信息,请参阅“触发工作流的事件”。 例如,ffac537e6cbbf934b08745a378932722df287a53
。
PS:官方提供的例子使用的是 $(date +%s)
时间戳,但我还没探索出在环境变量里拼接字符串的方法。
搭建本地 runner
镜像构建完事了,还得在本地的服务器上跑。
很简单,就是把镜像 pull 下来,然后 docker compose up
就行,现在我们把这一步也加入到 workflow 里。
添加 runner
访问这个页面: https://github.com/star-plan/aihub/settings/actions/runners
点击 New self-hosted runner 按钮
选择对应的系统和架构,然后根据里面的命令来就完事了。
本文选择的是 Linux - x64 的方案
GitHub 提供的命令是这样(这里只是给出例子,实际要以自己的项目配置页面为准)
其中下载这一步可能会遇到问题,因为某些莫名其妙的原因,GitHub 访问不了,这时候需要使用 proxychains
工具,请自行搜索 + 配置。
PS:好家伙,这个 runner 居然有 180M
接着运行命令 runner
提示输入 runner group 名称,默认即可
提示需要输入 runner 名字,我输入了个
aihub
接着还可以输入 label 啥的,根据需求来就行
配置搞定之后就启动 runner
安装服务
用 ./run.sh
启动的 runner 并不稳定,退出登录之后就无了,就算使用 &
或者 Ctrl+Z
切换到后台执行,也不是那么稳定。
GitHub runner 可以作为 Linux 服务运行,使用也很简单。
先关掉正在运行的 runner
安装服务
启动服务
更多操作请查看第四条参考资料。
查看 runner 列表
在 GitHub 页面上查看当前运行的 runner
地址: https://github.com/star-plan/aihub/settings/actions/runners
可以看到已经有一个叫 aihub 的 runner 了
runner 网络代理
这波我只能说 GitHub 太贴心了!他已经考虑到了不能上 GitHub 的情况,他真的,我哭死😭
可以在环境变量里设置代理,也可以在 .env
文件里配置,这里我还是选 .env
吧。
更多关于搭建本地 runner 的文档,可以查看参考资料的第三条。
使用本地 runner 部署服务
老规矩,使用 docker-compose 来编排服务。
先创建个目录,里面存放 docker-compose.yml
和一些持久化的文件。
本例子的路径是: /home/apps/aihub
镜像部分我用了环境变量,因为每次构建的镜像 tag 都不一样,我要在 workflow 里将 tag 写入 .env
文件。当然也可以写固定 latest
。
.env
文件是这样
OK,总算是到了最后一步,继续编辑我们的 workflow ,增加一个 deployment
任务。
注意:
jobs 默认是并行执行的,所以需要在 deployment 任务里加上
needs
配置,等 build 完了再部署
使用
jobs.<job_id>.needs
标识运行此作业之前必须成功完成的所有作业。 它可以是一个字符串,也可以是字符串数组。 如果某个作业失败或跳过,则所有需要它的作业都会被跳过,除非这些作业使用让该作业继续的条件表达式。 如果运行包含一系列相互需要的作业,则故障或跳过将从故障点或跳过点开始,应用于依赖项链中的所有作业。 如果希望某个作业在其依赖的作业未成功时也能运行,请在jobs.<job_id>.if
中使用always()
条件表达式。
deployment
任务是在本地执行的,所以runs-on
通过多个 label 选择了本地 runner
执行
docker compose
命令的时候工作目录是在 GitHub Action 工具的_work
目录里,所以需要指定--project-directory
参数,或者通过--env-file
指定.env
文件位置
查看执行结果
在 GitHub Action 页面可以查看执行结果。
搞定!
参考资料
https://docs.github.com/zh/actions/learn-github-actions/variables
https://docs.github.com/zh/actions/publishing-packages/publishing-docker-images
https://docs.github.com/zh/actions/using-jobs/using-jobs-in-a-workflow
https://docs.docker.com/compose/environment-variables/set-environment-variables/
文章转载自:程序设计实验室
评论