如果你的源碼庫採用單一儲存庫( Monorepo )的策略,並透過私有子模組( private submodule )組織 app 的源碼,那麼在部署到 Vercel 時,會遇到下面這個錯誤訊息:

WARN: failed to fetch one or more git submodules: Failed to clone 'my-submodule' a second time, aborting

根據官方論壇上的討論(#44),這是因為 Vercel 目前不支援此一特性。距今已過 4 年,因此有很大的機會,Vercel 將來也沒打算支援的樣子,那麼要怎麼辦呢?

由於 Vercel 本身是可以透過 HTTP 協議去拉取子公開儲存庫的,於是一位使用者 beeinger 提出兩個解方(連結)。第一個方式是在 .gitmodules 改用 http 加上指定 access token 的方式拉子模組,作法如下。

[submodule "<repo-name>"]
path = <folder-name>
url = https://<github-token>@github.com/<owner-name>/<repo-name>.git

這個方式的缺點是,你的 access token 必須要寫死在 .gitmodules。我想不少人會對此有疑慮。

因此,他又提出第二個方式,原理差不多,但拉子模組的過程改用一個 workround script,在臨時目錄中初始化一個空的 Git 儲存庫,添加子模組的遠端來源,並抓取所需的版本。最後,腳本會把子模組的內容移動到指定的路徑,並清理臨時目錄,確保子模組在部署過程中能夠正確載入。採用這方法的好處是 access token 可以透過環境變數載入。

如果不想用上面這兩種方式,junhoyeo 在 2022 年寫了一個 npx 工具 - vercel-submodules

npx vercel-submodules --all
npx vercel-submodules --paths specific-module-a specific-module-b

這個工具透過 $GITHUB_TOKEN 這個環境變數讀取Github finegrant personal token

npx vercel-submodules --fg-token ${# fine-grained personal access token}

如果是 Gitlab ,你只能用 Gitlab 的 Personal Access Token

npx vercel-submodules --fg-token ${gitlab_personal_token}

在 Vercel 的使用方式是到 Vercel 專案設定頁面,進行下面三個設定。

  1. 設定 $GITHUB_TOKEN 環境變數
  2. build 指令要改成 turbo run build --filter ${path-to-submodule}
  3. install 指令要改成 npx vercel-submodules && npm install

比較之後,我最後採用了 vercel-submodules 的做法。