🎃

Turborepoでnext-sitemapが見れなくなった場合の直し方

2022/12/07に公開

next-sitemapをYarn Workspace + Turborepoで使った際に、「キャッシュを復元したデプロイで、サイトマップが見れない」状況に陥った。

  • packages
    • web
      • public
        • sitemap*.xml
      • package.json
  • package.json
  • turbo.json

例えばこのようなモノレポになっていたとして、Turborepoでwebをビルドするとする。

例えばこのようにブランチを切ってマージしたとする。

 Tasks:    1 successful, 1 total
Cached:    1 cached, 1 total
  Time:    1.XXXs >>> FULL TURBO

A-->BA-->mainの差分が同じなので、mainのデプロイでキャッシュが再利用される。

サイトは閲覧できるが、postbuildbuildタスクに含まれていないため、サイトマップが復元されない。 (1 cachedとなっていることから、buildのタスクしかキャッシュできていないことが分かる。)

かといって postbuildをタスクに含めると、キャッシュ復元時だけpostbuildをわざわざ発火しないといけない。話がややこしくなる。

https://github.com/vercel/turbo/discussions/1027#discussioncomment-3683478

だいぶ前からディスカッションで問題定義されているが、公式の回答がなく、Sam氏の提案する方法がturbo@1.6.3現在では最適解だと判断した。

つまるところpostbuildを使わない方向で行く。

方法

1. sitemapコマンドを変更

packages/web/package.json
-    "postbuild": "next-sitemap"
+    "sitemap": "next-sitemap"

どうせ走らないので独自コマンドとして定義する。

2. デプロイタスクを定義

turbo.json
{
  "$schema": "https://turbo.build/schema.json",
  "pipeline": {
    "build": {
      "outputs": [".next/**"]
    },
    "dev": {
      "cache": false
    },
+    "sitemap": {
+      "dependsOn": ["build"],
+      "outputs": ["public/sitemap*.xml"]
+    },
+    "deploy": {
+      "dependsOn": ["build", "sitemap"],
+      "outputs": []
+    }
  }
}

改めてサイトマップ生成とデプロイのタスクを定義する。

3. Vercelビルドコマンドを変更

- cd ../.. && npx turbo run build --filter=<パッケージ名(部分一致)>...
+ cd ../.. && npx turbo run deploy --filter=<パッケージ名(部分一致)>...

builddeployに変える。

「パッケージ名」はフォルダ名ではなくpackage.jsonを参照すること。"name": "web"と書かれていれば、パッケージ名はwebでいい。

 Tasks:    2 successful, 2 total
Cached:    2 cached, 2 total
  Time:    1.XXXs >>> FULL TURBO

こうすることで、毎回確実にsitemapコマンドが実行され、その結果も含めてキャッシュが復元される。(2 cachedとなっていることから、sitemapタスクが復元されたことが分かる)

Discussion