问小白 wenxiaobai
资讯
历史
科技
环境与自然
成长
游戏
财经
文学与艺术
美食
健康
家居
文化
情感
汽车
三农
军事
旅行
运动
教育
生活
星座命理

使用 GitHub Actions 实现项目的持续集成(CI)

创作时间:
作者:
@小白创作中心

使用 GitHub Actions 实现项目的持续集成(CI)

引用
CSDN
1.
https://blog.csdn.net/weixin_59624686/article/details/138330218

**GitHub Actions是GitHub推出的一款持续集成(CI)服务,它允许开发者创建自定义工作流,自动化开发过程中的各种任务。本文将详细介绍GitHub Actions的基本概念、工作流文件的配置方法,并通过一个OpenWrt编译实例,帮助读者快速掌握GitHub Actions的使用。

什么是 GitHub Actions

  • GitHub Actions是GitHub推出的持续集成(Continuous Integration,简称CI)服务
  • 它允许你创建自定义工作流,你可以使用这些工作流来自动化开发过程
  • 它提供了整套虚拟服务器环境,基于它可以进行构建、测试、打包、部署项目等等操作
  • 每个GitHub仓库都可以配置一个或多个工作流程,通过.github/workflows目录中的YAML文件定义
  • 简单来讲就是将软件开发中的一些流程交给云服务器自动化处理,比方说开发者把代码push到GitHub后它会自动测试、编译、发布
  • 有了持续集成服务开发者就可以专心于写代码,其它乱七八糟的事情就不用管了,这样可以大大提高开发效率
  • 持续集成(CI/CD)主要有三个:持续集成、持续交付、持续部署
  • 我们一般的软件开发流程是:
    1. 开发人员本地代码commit,push
    2. 通过git hook触发自动化测试
    3. 测试通过后,合并发布分支
    4. 通过git hook触发自动部署服务
  • 这里简单的描述了软件开发周期,当然实际上会更加复杂
  • CI/CD是由很多操作组成的,比如执行自动化测试、分支合并、服务部署等,而GitHub把这一系列的操作都称为Actions
  • 当然GitHub创新点还不仅于此,不同的项目可能都会使用到相类似的Action,GitHub允许开发者把action写成独立的脚本文件,存放到代码仓库,使得其他开发者可以引用
  • GitHub提供了一个官方市场:GitHub Action Market
  • 在这里可以搜索到你想要的任何actions,直接引用别人造好的轮子

基础概念

  • Workflows(工作流):持续集成一次运行的过程,可以添加到存储库中的自动化过程
  • 工作流由一个或多个作业组成,可以由事件调度或触发
  • Event(事件):触发工作流的特定动作;例如,向存储库提交pr或pull请求
  • Jobs(作业):在同一跑步器上执行的一组步骤;默认情况下,具有多个作业的工作流将并行运行这些作业
  • Steps(步骤):可以在作业中运行命令的单个任务;步骤可以是操作,也可以是shell命令
  • 作业中的每个步骤都在同一个运行程序上执行,从而允许该作业中的操作彼此共享数据
  • Actions(操作):操作是独立的命令,它们被组合成创建作业的步骤
  • 操作是工作流中最小的可移植构建块
  • 你可以创建自己的动作,或者使用GitHub社区创建的动作
  • 每个step可以依次执行一个或多个命令(action)
  • Runners(运行器):安装了GitHub Actions运行器应用程序的服务器
  • GitHub托管的运行器基于Ubuntu Linux、Microsoft Windows和macOS,工作流中的每个作业都在一个新的虚拟环境中运行

Workflow 文件

  • GitHub Actions的配置文件叫做workflow文件(官方中文翻译为“工作流程文件”)
  • 存放在代码仓库的.github/workflows目录中
  • workflow文件采用YAML格式,文件名可以任意取,但是后缀名统一为.yml或.yaml,比如icpctj.yml
  • 一个库可以有多个workflow文件,GitHub只要发现.github/workflows目录里面有.yml或.yaml文件,就会按照文件中所指定的触发条件在符合条件时自动运行该文件中的工作流程
  • 在Actions页面可以看到很多种语言的workflow文件的模版,可以用于简单的构建与测试
  • 下面是一个简单的workflow文件示例:

Workflow 语法

  • name

  • workflow的名称,GitHub在仓库的操作页面上显示workflow的名称

  • on

  • 触发workflow的GitHub事件的名称

  • 比如示例中的触发事件(使用单个事件)是push,即在代码push到仓库后被触发

  • on字段也可以是事件的数组,多种事件触发(使用多个事件),比如在push或pull-request时触发:

  • 某些事件具有活动类型,可让你更好地控制工作流的运行时间

  • 使用on.<event.name>.types定义将触发工作流运行的事件活动类型(使用活动类型)

  • 例如,issue-comment事件具有created、edited和deleted活动类型

  • 如果工作流在label事件上触发,则每当创建、编辑或删除标签时,它都会运行

  • 如果为created事件指定label活动类型,则工作流将在创建标签时运行,但不会在编辑或删除标签时运行

  • 如果指定多个活动类型,则只需要发生其中一种事件活动类型就可触发工作流

  • 如果触发工作流的多个事件活动类型同时发生,则将触发多个工作流运行

  • 例如,创建或标记问题时,会触发以下工作流

  • 如果创建了一个带两个标签的问题,则将启动三个工作流运行:一个用于创建问题的事件,另外两个用于两个标记问题的事件

  • 某些事件具有筛选器,可让你更好地控制工作流的运行时间(使用筛选器)

  • 例如,push事件具有branches筛选器,该筛选器仅在发生目标为与branches筛选器匹配的分支的推送时(而不是在发生任何推送时)运行工作流

  • 如果为事件指定活动类型或筛选器,并且针对多个事件指定工作流触发器,则必须单独配置每个事件

  • 必须为所有事件附加冒号(:),包括没有配置的事件

  • 例如,具有以下on值的工作流将在以下情况下运行:

    1. 创建标签
    2. 推送到存储库中的main分支
    3. 推送到启用了GitHub Pages的分支
  • 完整的事件列表,请查看官方文档

  • 下面是一些比较常见的事件:

  • Jobs

  • 作业,workflow主要执行的核心任务

  • 表示要执行的一项或多项任务

  • 每一项任务必须关联一个ID(job.id),比如示例中的my.first.job和my.second.job

  • jobs.<job.id>

  • job.id里面的name字段是任务的名称

  • jobs.<job.id>.name

  • job.id不能有空格,只能使用数字、英文字母和-符号,而name可以随意,若忽略name字段,则默认会设置为job.id

  • job.id里面的needs表示识别在此作业运行之前必须成功完成的任何作业

  • jobs.<job.id>.needs

  • 当有多个任务时,可以指定任务的依赖关系,即运行顺序,否则是同时运行

  • 上面代码中,job1必须先于job2完成,而job3等待job1和job2的完成才能运行

  • 因此,这个workflow的运行顺序依次为:job1、job2、job3

  • runs-on

  • runs-on字段指定任务运行所需要的虚拟服务器环境,是必填字段

  • jobs.<job.id>.runs-on

  • 机器可以是GitHub托管的运行器或自托管的运行器

  • steps

  • steps字段指定每个任务的运行步骤,可以包含一个或多个步骤

  • jobs.<job.id>.steps

  • 步骤可以是运行命令、运行设置任务,或者运行仓库中的操作和Dcoker镜像发布等

  • 步骤开头使用-符号表示

  • 每个步骤可以指定以下字段:

    1. jobs.<job.id>.steps[*].id
  • 步骤的唯一标识符

  • 可以使用id在上下文中引用该步骤

    1. jobs.<job.id>.steps[*].if
  • 可以使用if条件来阻止步骤运行,除非满足条件

  • 您可以使用任何支持上下文和表达式来创建条件

    1. jobs.<job.id>.steps[*].name
  • 步骤显示在GitHub上的名称

    1. jobs.<job.id>.steps[*].uses
  • 选择要作为作业中步骤的一部分运行的操作

  • 操作是一种可重复使用的代码单位

  • 可以使用在与工作流、公共存储库或已发布的Docker容器映像相同的存储库中定义的操作

    1. jobs.<job.id>.steps[*].run
  • 使用操作系统的shell运行不超过21,000个字符的命令行程序

  • 如果不提供name,步骤名称将默认为run命令中指定的文本

    1. jobs.<job.id>.steps[*].working-directory
  • 使用working-directory关键字,你可以指定运行命令的工作目录位置

    1. jobs.<job.id>.steps[*].shell
  • 可以使用shell关键字,覆盖运行器操作系统中的默认Shell设置,以及作业的默认值

    1. jobs.<job.id>.steps[*].with
  • 由操作定义的输入参数的map

  • 每个输入参数都是一个键/值对

  • 输入参数被设置为环境变量

  • 该变量的前缀为INPUT_,并转换为大写

  • 为Docker容器定义的输入参数必须使用args

    1. jobs.<job.id>.steps[*].env
  • 设置供步骤在运行器环境中使用的变量

  • 也可以设置用于整个工作流或某个作业的变量

    1. 下面是一些常见的字段:
  • 其中uses和run是必填字段,每个步骤只能有其一

  • 同样名称也是可以忽略的

  • action

  • action是GitHubActions中的重要组成部分,这点从名称中就可以看出,actions是action的复数形式

  • 它是已经编写好的步骤脚本,存放在GitHub仓库中

  • 对于初学者来说可以直接引用其它开发者已经写好的action

  • 可以在官方action仓库或者GitHubMarketplace去获取

  • 此外AwesomeActions这个项目收集了很多非常不错的action

  • 既然action是代码仓库,当然就有版本的概念

  • 引用某个具体版本的action:

  • 一般来说action的开发者会说明建议使用的版本

实例:编译 OpenWrt

  • 既然是编译OpenWrt那么workflow的名称就叫BuildOpenWrt
  • 触发事件我选择了push
  • 个人常用的OpenWrt编译环境使用的是Ubuntu18.04,所以任务所使用的虚拟环境也一样
  • 我并不确定系统中是否有编译所需要依赖,所以第一个步骤是安装依赖软件包
  • 由于我使用的是一个空仓库,所以第二个步骤使用Git去拉取OpenWrt官方源码
  • TIPS:如果是有源码的仓库,可以引用actions/checkout这个官方action把源码签出到工作目录中
  • 工作目录也就是在Actions中执行命令的根目录,其绝对路径为/home/runner/work/REPO_NAME/REPO_NAME,环境变量为$GITHUB_WORKSPACE
  • 然后还需要拉取feeds,它是扩展软件包源码,所以需要单独拉取
  • 既然都是拉取源码,所以就都放在一起吧
  • 由于这只是尝试,所以第三个步骤就让它生成一个默认的配置文件
  • 由于每个步骤都会回退到工作目录,所以前面还需要加一条进入buildroot的命令
  • 第四个步骤是下载第三方软件包(俗称dl库)
  • 最后为了防止下载不完整导致编译失败,加了显示不完整文件和删除不完整文件的命令
  • 第五个步骤进入到最重要的开始编译环节
  • 同样是先进入buildroot,为了能更快的编译,我自信的选择了多线程编译且不显示详细日志
  • 最后编译出的二进制文件如何取出来呢?
  • 官方有个action叫upload-artifact,它可以将虚拟环境中的指定文件打包上传到Actions页面
  • 为了方便我选择了上传整个bin目录,文件名为OpenWrt
  • 最后展示一下完整workflow文件:
  • 最后push到仓库运行
© 2023 北京元石科技有限公司 ◎ 京公网安备 11010802042949号