利用github actions实现hexo博客的自动部署


之前从阮一峰老师的博客,了解了github 推出的 github actions,有尝试过一点好玩的定时任务。最近想起,自己好久没有更新博客了,于是想来用 github actions 实现基于 hexo 框架的博客自动部署。(你看到的就是通过github actions 自动部署的~~)。

什么是 Github Actions

Automate, customize, and execute your software development workflows right in your repository with GitHub Actions. You can discover, create, and share actions to perform any job you’d like, including CI/CD, and combine actions in a completely customized workflow.

Github Actions 是 Github 官方推出的持续集成服务,它允许你自定义工作流程,以满足自身的需求。我们可以通过创建工作流程文件,实现自动化构建、测试、打包、部署项目等。

Github Actions的工作流程语法

Github Actions的几个专业术语:

  • workflow (工作流程):持续集成一次运行的过程,就是一个 workflow。
  • job (任务):一个 workflow 由一个或多个 jobs 构成,含义是一次持续集成的运行,可以完成多个任务。
  • step(步骤):每个 job 由多个 step 构成,一步步完成。
  • action (动作):每个 step 可以依次执行一个或多个命令(action)。

Github Actions的配置文件叫做 workflow,存放于代码仓库根目录下的 .github/workflows目录下。

workflow 文件采用 YAML 格式,文件名可以任意命名,但统一后缀为 .yml。一个仓库可以拥有多个workflow文件, Github 只要发现 .github/workflows 目录下存在 .yml文件,就会自动运行该文件。

workflow 文件的配置字段非常多,可参考官方文档。(中文地址)

文件示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
# This is a basic workflow to help you get started with Actions

name: HELLO GITHUB ACTION

# Controls when the workflow will run
on:
# Triggers the workflow on push or pull request events but only for the main branch
push:
schedule:
- cron: '0 0 * * *'

# Allows you to run this workflow manually from the Actions tab
workflow_dispatch:

# A workflow run is made up of one or more jobs that can run sequentially or in parallel
jobs:
# This workflow contains a single job called "build"
build:
# The type of runner that the job will run on
runs-on: ubuntu-latest

# Steps represent a sequence of tasks that will be executed as part of the job
steps:
# Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it
# - uses: actions/checkout@v2
- name: 'Checkout codes'
uses: actions/checkout@v2

# Runs a single command using the runners shell
- name: Get weather
run: bash ./weather.sh

# Runs a set of commands using the runners shell
- name: Get Date
run: echo "REPORT_DATE=$(TZ=':Asia/Shanghai' date '+%Y-%m-%d %T')" >> $GITHUB_ENV

- name: Send email
uses: dawidd6/action-send-mail@master
with:
server_address: ${{ secrets.MAIL_SERVICE }}
server_port: 465
username: ${{ secrets.MAIL_USERNAME }}
password: ${{ secrets.MAIL_PASSWORD }}
subject: 天气预报 (${{env.REPORT_DATE}})
html_body: file://result.html
to: jiaochunxiao2008@163.com
from: 天气小助手
content_type: text/html
  • name: workflow名称,可省略,默认为当前workflow文件名
  • on: 触发 workflow的条件,通常是某些事件,上述示例中当git push时,就会触发。
    on 字段也可以为数组,表示一系列事件都可以触发,如:
    1
    on: [push, pull_request]
    完整事件列表,可参考官方文档
    • on.<push|pull_request>.<tags|branches>
      指定触发事件事,限定的分支或标签
      1
      2
      3
      4
      on:
      push:
      branches:
      - master
    • on.schedule
      您可以使用 POSIX cron 语法安排工作流程在特定的 UTC 时间运行。 预定的工作流程在默认或基础分支的最新提交上运行。 您可以运行预定工作流程的最短间隔是每 5 分钟一次。
  • jobs
    工作流程运行包括一项或多项作业。 作业默认是并行运行。 要按顺序运行作业,您可以使用<job_id>needs 关键词在其他作业上定义依赖项。每个作业在 runs-on 指定的运行器环境中运行。
    在工作流程的使用限制之内可运行无限数量的作业。
    • jobs.<job_id>.name
      workflow 文件的主体是jobs字段,表示要执行的一项或多项任务。
      jobs字段里面,需要写出每一项任务的job_id,具体名称自定义。job_id里面的name字段是任务的说明。
      1
      2
      3
      4
      5
      jobs:
      my_first_job:
      name: My first job
      my_second_job:
      name: My second job
    • jobs.<job_id>.needs
      识别在此作业运行之前必须成功完成的任何作业。 它可以是一个字符串,也可以是字符串数组。 如果某个作业失败,则所有需要它的作业都会被跳过,除非这些作业使用让该作业继续的条件表达式。
      1
      2
      3
      4
      5
      6
      jobs:
      job1:
      job2:
      needs: job1
      job3:
      needs: [job1, job2]
      在此示例中,job1 必须在 job2 开始之前成功完成,而 job3 要等待 job1 和 job2 完成。
    • jobs.<job_id>.runs-on
      必填。 要运行作业的机器类型。 机器可以是 GitHub 托管的运行器或自托管的运行器。
    • jobs.<job_id>.steps
      steps字段指定每个 Job 的运行步骤,可以包含一个或多个步骤。每个步骤都可以指定以下三个字段。
      • jobs.<job_id>.steps.name:步骤名称
      • jobs.<job_id>.steps.run:该步骤运行的命令或者 action。
      • jobs.<job_id>.steps.env:该步骤所需的环境变量。

了解完基本的Github Actions知识后,下面开始步入正题:如何利用github actions实现hexo博客的自动部署呢?

如何利用github actions实现hexo博客的自动部署

由于我的博客地址是由两个仓库构成的,一个是博客的源码地址(blog-source,非公开),一个是博客的部署地址(jiaochunxiao.github.io)的,公开的。所以以下步骤将展示两个仓库下的自动化部署流程。
当然,如果你的博客是通过同一仓库,不同分支完成的,也可以参考本文,适当调整完成。

生成公私钥

在仓库下执行以下命令:

1
ssh-keygen -t rsa -b 4096 -C "$(git config user.email)" -f github-deploy-key -N ""

目录将生成两个文件

  • github-deploy-key.pub: 公钥文件
  • github-deploy-key: 私钥文件

切记不要将此文件上传至github仓库中。

为博客源码仓库添加私钥

将github-deploy-key文件中的内容添加到,博客源码仓库(blog-source) 的 secret 中。

blog-source -> setttings -> secrets -> new repository secret:

添加后如图:

为部署仓库(xxx.github.io)添加公钥

将github-deploy-key.pub文件中的内容添加到 部署仓库的deploy keys中。

xxx.github.io -> setttings -> deploy keys -> add new deploy key:

添加后如图;

源码博客编写 Github Actions

在博客源码目录下创建:./github/workflow/deploy.yml文件。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
name: deploy

on:
push:
branches:
- master

jobs:
build-and-deploy:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/setup-node@v2
with:
node-version: 14.17.4
# registry-url: https://registry.npmmirror.com/

- name: setup hexo
env:
ACTION_DEPLOY_KEY: ${{ secrets.HEXO_DEPLOY_KEY }}
run: |
mkdir -p ~/.ssh/
echo "$ACTION_DEPLOY_KEY" > ~/.ssh/id_rsa
chmod 600 ~/.ssh/id_rsa
ssh-keyscan github.com >> ~/.ssh/known_hosts
git config --global user.name 'jiaochunxiao'
git config --global user.email 'jcx13627607951@gmail.com'
npm install

- name: build
run: npm run clean && npm run deploy

hexo配置修改

在源码仓仓库下的 _config.yml 文件中,增加以下内容

1
2
3
4
deploy:
type: git
repository: git@github.com:jiaochunxiao/jiaochunxiao.github.io.git
branch: master

此处repo填写ssh形式,填写https模式可能会导致失败

部署验证

git push后:

部署成功:

参考