使用GitHub Actions实现基于Hexo的GitHub Pages自动部署
Samersions ZHONG Lv1

不少程序员喜欢使用GitHub Pages配合Hexo部署自己的静态博客,GitHub Pages的优势是免费的托管以及可以自定义域名,而且针对自定义的域名还能获得自动签发的SSL证书,避免了自行购买证书的花费或是免费证书有效短的繁琐。笔者的这个博客也是托管在GitHub Pages上的。但静态博客生成页面需要搭建一定的环境,如果手上没有电脑恰好又想对文章做细微的修改会比较麻烦,而且没办法使用写了一半的草稿。

GitHub Actions是GitHub推出的持续集成服务,这玩意儿跟Travis CI是一样的,但是它有个优势是免费版也支持GitHub私有仓库,也就是说笔者可以把Hexo博客的源码放在GitHub的私有仓库里面,防止堆积如山的草稿和初稿糟糕的行文博客的配置文件暴露,并配置GitHub Actions自动部署。当新的源文件提交到私有仓库后,GitHub Actions会自行编译并推送指定GitHub Pages仓库。

免费版的GitHub账号每月支持2000分钟的GitHub Actions执行时长,一般来说编译并部署一次Hexo的博客耗时不会超过1分钟,因此在本地充分调试的情况下,每月2000分钟的执行时长绰绰有余了。

实现上述过程非常简单:

准备Hexo源文件

  1. 首先需要准备一套Hexo博客的源文件,你可以使用自己原有的博客源文件,或使用如下命令生成一个:
1
hexo init
  1. 安装 hexo-deployer-git 插件,并配置 _config.ymldeploy 节点。该节点会在初始化源文件时自动生成,若不存在可自行添加:
1
2
3
4
deploy:
type: git
repo: GitHub Pages所在仓库的远程URL
branch: GitHub Pages使用的分支

如果你的GitHub账号已经配置了SSH密钥对,推荐使用 SSH URL 进行测试;否则可临时填入 HTTPS URL 进行测试,后期再更换为 SSH URL。

  1. 编译Hexo的源文件,运行如下命令测试一下能否部署到GitHub Pages的仓库:
1
hexo d

如果使用 SSH URL 进行推送,则文件会立即上传,若使用 HTTPS URL 会要求输入GitHub账号的密码。测试成功后就可以进入下一步了。

  1. 完成测试后将源码提交并推送到一个私有的仓库备用。

配置GitHub Actions

  1. 生成单独的SSH密钥对。

上节进行部署时,可能使用了HTTPS + 控制台手动输入密码SSH + 账户全局密钥对编译的文件进行推送。这两种方式,前者不适用于自动部署,因为自动部署脚本无法手动输入密码;后者虽然能成功部署,但使用的密钥能访问该账户名下的所有仓库,若不慎泄露会造成麻烦。因此可以为GitHub Pages所在的仓库单独配置一套SSH密钥对,密钥只能用于该仓库的访问:

1
ssh-keygen -t rsa -C "GitHub账户邮箱"
  1. 为GitHub Pages仓库添加 Deploy keys

进入GitHub Pages仓库的Settings页面,在Deploy keys处添加上一步生成的密钥对公钥,注意要允许写入。

  1. 为Hexo源码仓库添加私钥。

若要使用GitHub Actions进行推送,就必须将刚刚生成的私钥一并添加到配置文件中,虽然源码仓库是私有的,但是将私钥明目张胆地放在源代码里面非常不优雅。此时可以使用GitHub提供的Secrets功能为仓库添加加密环境变量,这个变量只有获得了授权的客户端才能正常读取,非常适合公开仓库的持续集成服务(如公开仓库 + Travis CI)。

进入Hexo源码仓库的Settings页面,在Secrets处添加一个新的加密环境变量,笔者将变量名设置为DEPLOY_KEY,内容为第1步生成的私钥。

  1. 为Hexo源码仓库添加GitHub Actions脚本。

有两种方式为当前仓库添加GitHub Actions脚本:

  • 通过仓库的Actions辅助自动生成,可以在各个模板里选择。
  • 手动在仓库源码添加.github/workflow/*.yml配置文件。

在这里笔者选择第二种方式,添加.github/workflows/main.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
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
name: Deploy to blog.samersions.net

push or pull request

# 这里可以设置不同的分支,比如在同一个源码仓库,利用两个不同的分支存储两个不同的博客,
# 可以在不同分支的配置下设置不同的分支触发,下面假设Hexo文件保存在source分支
on:
push:
branches: [ source ]
pull_request:
branches: [ source ]

jobs:
build:
runs-on: ubuntu-latest

# 使用模板库里面Checkout模板克隆并切换到指定分支,这里为source
steps:
- name: Checkout Repository master branch
uses: actions/checkout@master
with:
ref: source

# 搭建Node.js环境供Hexojs使用
- name: Setup Node.js 10.x
uses: actions/setup-node@master
with:
node-version: "10.x"

# 安装Hexojs
- name: Setup Hexo Dependencies
run: |
npm install hexo-cli -g
npm install

# 设置私钥,这里会读取在Secrets里设置的私钥,并通过环境变量与构建程序进行交互
- name: Setup Deploy Private Key
env:
HEXO_DEPLOY_PRIVATE_KEY: ${{ secrets.DEPLOY_KEY }}
run: |
mkdir -p ~/.ssh/
echo "$HEXO_DEPLOY_PRIVATE_KEY" > ~/.ssh/id_rsa
chmod 600 ~/.ssh/id_rsa
ssh-keyscan github.com >> ~/.ssh/known_hosts

# 设置你的Git用户信息,会显示在Commit记录上,
# 如果与GitHub的账户信息相同,Commit会归到你的GitHub账户下面。
- name: Setup Git Infomation
run: |
git config --global user.name '用户名'
git config --global user.email '邮箱'

# 编译并部署
- name: Deploy Hexo
run: |
hexo clean
hexo generate
hexo deploy
  1. 修改 hexo-deployer-git 的配置。

如果在上一节设置的hexo-deployer-git配置使用了HTTPS URL,需要修改为SSH URL,否则无法通过SSH密钥对进行推送:

1
2
3
4
deploy:
type: git
repo: GitHub Pages所在仓库的远程SSH URL
branch: GitHub Pages使用的分支
  1. 将上述文件一并提交并推送到Hexo源码仓库,稍等片刻即可在GitHub Pages页面看到自动部署的博客。部署情况可在Hexo源码仓库的Actions页面看到。