【実務・中級編】npmの「prepare」と「prepublishOnly」の微妙な違い:公開前フックでリリース事故をゼロにする – ビルド・パッケージ管理ツール生産性向上バイブル

npm公開プロセスの深淵:prepareとprepublishOnlyを制し、リリース事故を根絶せよ

多くのエンジニアが「なんとなく」で使い分けている`npm`のライフサイクルスクリプト。しかし、プロダクション環境で「ビルドの成果物が含まれていない」「CIでテストが走らずに公開された」といった事故を防ぐためには、npmの実行エンジンがパッケージをどのようにパッケージングし、レジストリに送り込んでいるかの「裏側」を理解する必要があります。

本記事では、テックリードの視点から、npmの公開ライフサイクルをハックし、開発体験(DX)と堅牢性を両立させるためのアーキテクチャを伝授します。

—

1. ライフサイクルスクリプトの「真実」:なぜ混乱するのか

npmには似た名前のフックが複数存在し、その挙動は「どのタイミングで実行されるか」によって厳密に定義されています。まずは、この不可解な迷宮を論理的に整理しましょう。

実行順序と責務の分離

公開時(`npm publish`)に実行される主なフックの順序は以下の通りです。

1. `prepare`: ローカルでの`npm install`(引数なし)時、および`npm publish`の直前に実行。「配布物の構築」に最適です。
2. `prepack`: パッケージがtarballにパックされる直前に実行。
3. `prepublishOnly`: `npm publish`時のみ実行。「公開前の最終チェック(テスト実行など)」に最適です。

なぜ`prepare`と`prepublishOnly`を混同してはいけないのか?
`prepare`は`npm install`時にも走ります。ここに重いテストや公開用の制約を含めると、メンバーがライブラリをインストールするたびにCI級の負荷がかかり、開発スピードが鈍化します。逆に、`prepublishOnly`はインストール時には走らないため、ここを「ビルド」に使ってしまうと、レジストリにはソースコードしか上がらず、利用者は動かないコードをダウンロードすることになります。

—

2. 事故ゼロを実現する「ベストプラクティス」設定

公開プロセスを自動化しつつ、ヒューマンエラーを排除するための`package.json`の設計は以下の形が理想です。

{
“name”: “my-library”,
“version”: “1.0.0”,
“files”: [
“dist”
],
“scripts”: {
“build”: “tsc –project tsconfig.json”,
“test”: “jest”,
“prepare”: “npm run build”,
“prepublishOnly”: “npm test && npm run lint”
}
}

この構成が「最強」である理由

  • `files`フィールドの活用: `.npmignore`は無視されるリスクがあるため、明示的なホワイトリスト方式(`files`フィールド)を採用します。`dist`ディレクトリ以外はレジストリに上げないという「意思表示」です。
  • `prepare`の役割: ライブラリをローカルにインストールした時点で確実に`dist`が生成されるため、開発者は「ビルドし忘れてPRを送る」という恥ずかしいミスから解放されます。
  • `prepublishOnly`の番兵: 公開コマンドを叩いた瞬間にテストが走り、失敗すれば即座に公開プロセスが中断されます。これにより、テストが通っていないコードが世界に公開されるリスクを物理的にゼロにします。

—

3. チーム開発で差をつける:生産性を最大化するテクニック

隠れたキーボードショートカット:`npm run`の省略

CLIでの開発効率を極限まで高めるには、`npm run

シェアする
toolsintronationalをフォローする
タイトルとURLをコピーしました