10
2

More than 5 years have passed since last update.

npmパッケージをgitリポジトリから取得したときに動くnpm scriptsを調べてみた

Posted at

やってみたこと

node.jsのアプリをいくつか書いていたら、共通の処理が出てきたのでライブラリ化したくなった。
でもあれやこれや…な理由でパブリックには公開できなかった。:cry:
そこでnpmのリポジトリには公開せず、プライベートなgitリポジトリからnpm i git+https://<git-repo>としてインポートすることにした。

npm prepublish の現状と今後どう変わっていくかという記事でnpm scriptsが実行される順序がまとめられていたので参考にしていたのだが、「publishされていないパッケージをgitのリポジトリから直接取ってきたらどうなんねん?」という疑問が湧いてきたので調べてみた。

検証環境

とりあえずnpm 5系と6系のふたつだけ調べました。
検証に使用したPCはmacOS Mojaveの入ったMacBook Proです。

1つ目
* node v8.11.4
* npm 5.6.0

2つ目
* node v8.12.0
* npm 6.4.1

検証方法

まずは下のようなpackage.jsonを用意する。scripts以外は基本的にnpm init -yで吐き出しただけ。

package.json
{
  "name": "npm-script-timings",
  "description": "This project is used to check timings when each npm scripts run.",
  "version": "1.0.0",
  "keywords": [],
  "license": "ISC",
  "main": "index.js",
  "scripts": {
    "prepublish": "echo \"##### prepublish #####\"",
    "prepare": "echo \"##### prepare #####\"",
    "prepublishOnly": "echo \"##### prepublishOnly #####\"",
    "prepack": "echo \"##### prepack #####\"",
    "pack": "echo \"##### pack #####\"",
    "postpack": "echo \"##### postpack #####\"",
    "publish": "echo \"##### publish #####\"",
    "postpublish": "echo \"##### postpublish #####\"",
    "preinstall": "echo \"##### preinstall #####\"",
    "install": "echo \"##### install #####\"",
    "postinstall": "echo \"##### postinstall #####\"",
    "preuninstall": "echo \"##### preuninstall #####\"",
    "uninstall": "echo \"##### uninstall #####\"",
    "postuninstall": "echo \"##### postuninstall #####\"",
    "preversion": "echo \"##### preversion #####\"",
    "version": "echo \"##### version #####\"",
    "postversion": "echo \"##### postversion #####\"",
    "pretest": "echo \"##### pretest #####\"",
    "test": "echo \"##### test #####\"",
    "posttest": "echo \"##### posttest #####\"",
    "prestop": "echo \"##### prestop #####\"",
    "stop": "echo \"##### stop #####\"",
    "poststop": "echo \"##### poststop #####\"",
    "prestart": "echo \"##### prestart #####\"",
    "start": "echo \"##### start #####\"",
    "poststart": "echo \"##### poststart #####\"",
    "prerestart": "echo \"##### prerestart #####*\"",
    "restart": "echo \"##### restart #####\"",
    "postrestart": "echo \"##### postrestart #####\"",
    "preshrinkwrap": "echo \"##### preshrinkwrap #####\"",
    "shrinkwrap": "echo \"##### shrinkwrap #####\"",
    "postshrinkwrap": "echo \"##### postshrinkwrap #####\""
  }
}

このpackage.jsonをプライベートgitリポジトリにpushし、別プロジェクトからnpm i git+https://<git-repo>.gitしたときのコンソールを見てみる。
今回はこのプロジェクトをnpm-script-timingsという名前のリポジトリにして、下のようなディレクトリ構成を取って確認してみた。別プロジェクトと言いながらサブディレクトリに含めてしまっているのは特に意味はありません。

npm-script-timings
├── package-lock.json
├── package.json        # 上記のpackage.json
└── another-project     # npm-script-timingsをインストールするプロジェクト

結果

パス中に登場してしまっている以下の名前は置換しています。

  • ホームディレクトリ -> $HOME
  • gitリポジトリのURL -> $GIT_REPO

npm 5.6.0の場合

インストール対象のスクリプトは、prepack -> postpack -> preinstall -> install -> postinstallの順で動作するようです。

> npm-script-timings@1.0.0 prepack $HOME/.npm/_cacache/tmp/git-clone-d3d05fce
> echo "##### prepack #####"

##### prepack #####

> npm-script-timings@1.0.0 postpack $HOME/.npm/_cacache/tmp/git-clone-d3d05fce
> echo "##### postpack #####"

##### postpack #####

> npm-script-timings@1.0.0 preinstall $HOME/.ghq/$GIT_REPO/another-project/node_modules/npm-script-timings
> echo "##### preinstall #####"

##### preinstall #####

> npm-script-timings@1.0.0 install $HOME/.ghq/$GIT_REPO/another-project/node_modules/npm-script-timings
> echo "##### install #####"

##### install #####

> npm-script-timings@1.0.0 postinstall $HOME/.ghq/$GIT_REPO/another-project/node_modules/npm-script-timings
> echo "##### postinstall #####"

##### postinstall #####
added 1 package in 7.137s

npm 6.4.1の場合

基本的な動作はnpm 5.6.0の場合と同じようですが、なぜかprepackpostpackが2回ずつ走っています。
そこまで問題にはならない気もしますが、意図した動作ではなさそう?

> npm-script-timings@1.0.0 prepack $HOME/.npm/_cacache/tmp/git-clone-8b6cee0a
> echo "##### prepack #####"

##### prepack #####

> npm-script-timings@1.0.0 postpack $HOME/.npm/_cacache/tmp/git-clone-8b6cee0a
> echo "##### postpack #####"

##### postpack #####

> npm-script-timings@1.0.0 prepack $HOME/.npm/_cacache/tmp/git-clone-79212f62
> echo "##### prepack #####"

##### prepack #####

> npm-script-timings@1.0.0 postpack $HOME/.npm/_cacache/tmp/git-clone-79212f62
> echo "##### postpack #####"

##### postpack #####

> npm-script-timings@1.0.0 preinstall $HOME/.ghq/$GIT_REPO/npm-script-timings/another-project/node_modules/npm-script-timings
> echo "##### preinstall #####"

##### preinstall #####

> npm-script-timings@1.0.0 install $HOME/.ghq/$GIT_REPO/npm-script-timings/another-project/node_modules/npm-script-timings
> echo "##### install #####"

##### install #####

> npm-script-timings@1.0.0 postinstall $HOME/.ghq/$GIT_REPO/npm-script-timings/another-project/node_modules/npm-script-timings
> echo "##### postinstall #####"

##### postinstall #####
added 1 package and audited 1 package in 12.331s
found 0 vulnerabilities

まとめ

npmリポジトリから取得するときと違って、gitリポジトリから直接取得しようとしたときにはnpm prepacknpm postpackが追加で動作するようです。
npmリポジトリに登録をしないときにはnpm publishをするタイミングがないので代わりにnpm packが行われる、というイメージでしょうか。

おまけ

TypeScript で作ったパッケージを TravisCI で npm に公開するときの Tipsでも述べられてる.gitignore.npmignoreの動作に気付かずに同じハマり方しました…。

10
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
10
2