用 GitHub Actions 替代 Vercel CI
· 技术问 题 描 述
前几天将博客部署回了 Vercel。本地 Vercel CLI 初始化项目、Vercel CI 构建并部署完网站之后,打开链接一看:捏妈滴,我 CSS 哪里去了?用 Devtools Network 一看,CSS 文件 404 Not Found,连带着几个 JavaScript chunks......
这个问题并不是前几天部署回去的时候遇到的,而是我很久之前、还没改回 Cloudflare Workers Site 的时候就遇到了这个问题:不管是什么项目,只要用了 Vercel CI 部署,CSS 和随机几个 JavaScript chunks 总会不翼而飞,给我干成了流汗黄豆 😅。
不过解决办法其实是有的。正如标题所言,我先用 GitHub Actions 构建完站点内容,再上传到 Vercel,而不是让 Vercel CI 一条龙服务解决。嗯,就这么简单。
CI 构建:从 Vercel CI 到 GitHub Actions
很久很久之前,GitHub Organization 想要使用 Vercel CI 必须得买 Team Plan,所以大家都会通过 GitHub Actions 使用 Vercel CI。
Vercel Action(amondnet/vercel-action
)便是其中一个例子。它其实就是一个 GitHub Actions 特供的 Vercel CLI,区别仅仅在于:
- 本地的 Vercel CLI 读取
.vercel
文件夹内的project.json
获取orgID
和projectID
,以便上传内容到 Vercel CI 进行构建; - Vercel Action 受限于
orgID
和projectID
明文存储在project.json
里、不能直接上传到 repo;同时,Vercel Action 不能直接访问你的 Vercel 账号,就像你本地安装了 Vercel CLI 也得执行vercel login
。所以,你必须得在 repo Secrets 里填写VERCEL_TOKEN
,VERCEL_ORG_ID
和VERCEL_PROJECT_ID
,供 Vercel Action 使用。
但是最上面已经提到了,Vercel CI 给我造成了不小的麻烦,所以我的网站不会再交给 Vercel CI 构建,而是交给 GitHub Actions。或许我可以将 Vercel 项目的根目录设置在 .output/public
,这样在 GitHub Actions 构建完站点内容之后,我就可以通过 Vercel Action 上传到 Vercel 了。如果你是这么想的话,那你就大错特错了:Vercel 会自动检测你的项目框架(比如我是 Nuxt,那么它识别出来之后自动给你选择 Nuxt 的预设),而它在给你套上预设之后会出现什么就不好说了。
不过,Vercel 虽然没有制作 Official Action,但是他们给出了一个与 GitHub Actions 一起使用的 方案。这是他们给出的一个 Action 配置文件:
name: Vercel Production Deployment
env:
VERCEL_ORG_ID: ${{ secrets.VERCEL_ORG_ID }}
VERCEL_PROJECT_ID: ${{ secrets.VERCEL_PROJECT_ID }}
on:
push:
branches:
- main
jobs:
Deploy-Production:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Install Vercel CLI
run: npm install --global vercel@latest
- name: Pull Vercel Environment Information
run: vercel pull --yes --environment=production --token=${{ secrets.VERCEL_TOKEN }}
- name: Build Project Artifacts
run: vercel build --prod --token=${{ secrets.VERCEL_TOKEN }}
- name: Deploy Project Artifacts to Vercel
run: vercel deploy --prebuilt --prod --token=${{ secrets.VERCEL_TOKEN }}
好像根本看不懂它在讲什么?别急,我来告诉你:
- 第一,
env
项指定需要用到的VERCEL_ORG_ID
和VERCEL_PROJECT_ID
、并从对应名称的 Secret 读取; - 第二,喜闻乐见的 checkout;
- 第三,全局安装 Vercel CLI;
- 第四,使用
VERCEL_TOKEN
拉取你的项目环境信息; - 第五,使用
VERCEL_TOKEN
在本地(即 GitHub Actions)构建你的站点内容; - 第六,使用
VERCEL_TOKEN
将构建好的内容上传到 Vercel。- 由于这一步标注了
--prebuilt
,所以上传到 Vercel 后不会再让 CI 构建、而是直接 deploy。
- 由于这一步标注了
现在你估计看懂了:这就是把 Vercel CI 的构建步骤交给 GitHub Actions 了。而且经过 GitHub Actions 构建之后,上面提到的 CSS 和随即几个 JavaScript chunks 不翼而飞 也不会出现了。
实战
假设我正要部署我手头上的 Nuxt 3 项目,包管理器就用我最近换的 Bun。
添加 Secrets
上面已经说到,Vercel Action 本质上就是一个 Vercel CLI,而这个 Action 代码也需要用到 Vercel CLI。所以你必须得在 repo Secrets 里添加 VERCEL_TOKEN
, VERCEL_ORG_ID
和 VERCEL_PROJECT_ID
。
VERCEL_ORG_ID
和 VERCEL_PROJECT_ID
就在上面提到的、你的项目根目录的 .vercel/project.json
里,分别对应 orgID
和 projectID
;至于 VERCEL_TOKEN
,懒得一步步教了,自己查一下怎么开一个(
编写 Action 配置文件
在项目根目录下创建 .github/workflows
目录,再在这个目录下创建一个 deploy.yml
,写入下述内容:
name: Deploy site
env:
VERCEL_ORG_ID: ${{ secrets.VERCEL_ORG_ID }}
VERCEL_PROJECT_ID: ${{ secrets.VERCEL_PROJECT_ID }}
on:
push:
branches:
- main
jobs:
CI:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@master
- name: Setup bun
uses: oven-sh/setup-bun@v1
with:
bun-version: latest
- name: Install Vercel CLI
run: bun install --global vercel@latest
- name: Pull Vercel Environment Information
run: vercel pull --yes --environment=production --token=${{ secrets.VERCEL_TOKEN }}
- name: Build Project Artifacts
run: vercel build --prod --token=${{ secrets.VERCEL_TOKEN }}
- name: Deploy Project Artifacts to Vercel
run: vercel deploy --prebuilt --prod --token=${{ secrets.VERCEL_TOKEN }}
对的,就是这么简单。除了 Bun / npm / pnpm / yarn 这种包管理器需要你自行配置,其余用 Vercel CLI 就可以搞定了。
将这个配置文件推到 GitHub 上,并且 Vercel 的项目设置保持原来用 Vercel CI 构建的配置,如果顺利跑完的话就可以收工了。