yarn workspacesでmonorepoを構成しているときに特定のpackageだけhoistの対象外にしたいというときがある。
そういうときにどうすればよいかというと、noHoist
オプションを単に使えばいいのだけどなぜかちゃんと書いてあるつもりなのにnoHoistが効かなくて困り果ててしまうケースがある。
このnoHoist
設定は実はめちゃくちゃややこしく罠しかないので覚書として書いておく。
nohoist in Workspaces | Yarn Blog
結論から
noHoistにはディレクトリパスではなくパッケージ名のglobを書かねばならない
です。
それでは順を追って見ていきましょう。
packageの名は
こういうmonorepo構成だったとする。このうちfun-utils
だけはhoistの対象にしたくないのでnoHoistしたいとする。
. ├─package.json └─packages ├─fun-domain ├─fun-interfaces └─fun-utils // hoistしてほしくない
そしてpackages/fun-utils
のpackage.json
はどうなっているかというとこう。
{ "name": "smile-utils", "version": "1.0.0", "dependencies": { "cross-env": "5.0.5" } }
おや?ディレクトリはpackages/fun-utils
なのにpackgae.json
のname
フィールドは「smile-utils
」ですね。
でもまあpackagesのフィールドはディレクトリなわけだし、普通こう書いてしまいますね。
"workspaces": { "packages": ["packages/*"], "nohoist": ["**/fun-utils", "**/fun-utils/**"] }
noHoistにディレクトリ名ベースのglobを書いた
ただこれではnoHoistの対象になりません
どうすればよいか。
"workspaces": { "packages": ["packages/*"], "nohoist": ["**/smile-utils", "**/smile-utils/**"] }
name
フィールドのglobに変えた
noHoist
は実はpackage.jsonのname
のglobにしないといけなかったのです……。
ちなみに
1度rootで yarn install
してあり、すでに各パッケージにlockファイルとnode_modules存在する状態からnoHoistの指定する場合は、noHoist対象node_modules
とyarn.lock
を削除しておかないといけないことを確認しています(v1.22.4)
yarn install --force
でもダメなので注意しましょう……。
😇