npmを個人的に解説していく
まだまだエンジニア初心者だが、知識をアウトプットして定着させていく。
記事を書く上で質問がいくつかでるので、誰か回答求む。
- npmにまつわるファイル・フォルダ
- package.json
- package-lock.json
- node-modules
- package.jsonの中身について
- name
- version
- private
- homepage
- dependencies
- scripts
- [npm <command> について](#npm <command> について)
- npm audit
- npm ci
- npm dedupe
- npm init
- npm install
疑問
- [疑問]packAとpackBでpackCを用いているが、それぞれが使っているpackCのバージョンが違う場合、どちらがインストールされるの?
- [[疑問]audit fix では修正されない場合ってどういうとき???](#[疑問]audit fix では修正されない場合ってどういうとき???)
- [[疑問]audit fix でアプデされるのはローカルのみ???](#[疑問]audit fix でアプデされるのはローカルのみ???)
- [[疑問]audit fix -f でもアプデされないパッケージは???](#[疑問]audit fix -f でもアプデされないパッケージは???)
npmにまつわるファイル・フォルダ
pythonとかはAnaconda等用いて仮想環境を作ってライブラリをインストールする(pip コマンド)。
フォルダを変えても同一仮想環境なら再びインストールとかしなくてもライブラリを使用できる。
npmはプロジェクトごと(=rootディレクトリごと)にパッケージをインストールする。
package.json
プログラマがnpm install によってインストールしたパッケージの一覧(=dependencies)がメイン。
他にもアプリを動作するうえでの必要な項目がいろいろ書かれている。詳細は下記参照
package-lock.json
package.json のdependenciesにあるパッケージが用いているパッケージを総まとめにしたもの
例えば
パッケージが2つ、packAとpackBが使用しているパッケージが以下の様だったとする。
- packA
- packC
- packD
- packB
- packC
- packE
すると、package-lockでは、
- packA
- packB
- packC
- packD
- packE
が記述される(って解釈してます)。
[疑問]packAとpackBでpackCを用いているが、それぞれが使っているpackCのバージョンが違う場合、どちらがインストールされるの?
node-modules
早い話がインストールしたパッケージのソースコードたち。
package.jsonの中身について
公式サイト
name
自分のパッケージを公開する際の名前?
公開する気が無くても、パッケージの区別のために名前をつけよう
If you plan to publish your package, the most important things in your package.json are the name and version fields as they will be required.
version
nameと同じポジション
そのパッケージのバージョンを表す
If you plan to publish your package, the most important things in your package.json are the name and version fields as they will be required.
private
trueにするとこのパッケージは公開されない
If you set "private": true in your package.json, then npm will refuse to publish it.
homepage
このパッケージのHPのURL
The url to the project homepage.
dependencies
このパッケージで利用しているパッケージたち
バージョンの指定等で書き方が様々ある様子
直接記入するのではなくnpm install
等を用いるべきだろう
scripts
早い話がショートカット
下の例でnpm run start
をするとbar ./test
が実行される
"scripts": {
"start" : "bar ./test"
}
npm <command> について
よく見かけるものを抜粋
npm audit
npm audit Run a security audit
Usage:
npm audit [fix]
Options:
[--audit-level <info|low|moderate|high|critical|none>] [--dry-run] [-f|--force]
[--json] [--package-lock-only]
[--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]]
[-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]]
[-ws|--workspaces]
Run "npm help audit" for more info
audit : 監査
インストールされているパッケージに脆弱性があるかをチェックする。
ここでいう脆弱性とは
パッケージのセキュリティ面に穴があり、ユーザーに攻撃される恐れがあるよ
ってイメージだと思う。
古いバージョンでは脆弱性が見つかったので、新しいやつに更新してね、ていうパッケージをこのコマンドで知らせてくれる。
試しに実行した結果:
react-dev-utils 0.4.0 - 12.0.0-next.60 -> [このパッケージのこのバージョンは]
Severity: high -> [脆弱性 high ]
Improper Neutralization of Special Elements used in an OS Command. - https://github.com/advisories/GHSA-5q6m-3h65-w53x
Depends on vulnerable versions of browserslist -> [脆弱性をもつこれらのパッケージのバージョンを使用している( = 依存している)]
Depends on vulnerable versions of globby
Depends on vulnerable versions of immer
Depends on vulnerable versions of inquirer
fix available via `npm audit fix --force` -> [このコマンドで修正してね]
Will install react-scripts@5.0.0, which is a breaking change -> [すると react-scripts@5.0.0 をインストールするけど、めっちゃ変更点あるよ]
node_modules/react-dev-utils
react-scripts >=0.8.0
Depends on vulnerable versions of @svgr/webpack
Depends on vulnerable versions of @typescript-eslint/eslint-plugin
Depends on vulnerable versions of eslint
Depends on vulnerable versions of eslint-config-react-app
Depends on vulnerable versions of eslint-loader
Depends on vulnerable versions of jest-watch-typeahead
Depends on vulnerable versions of optimize-css-assets-webpack-plugin
Depends on vulnerable versions of react-dev-utils
Depends on vulnerable versions of resolve-url-loader
Depends on vulnerable versions of webpack-dev-server
node_modules/react-scripts
npm audit fix
auditはチェックするだけだが、audit fix で実際にパッケージが更新される。
audit fix では修正されない場合、オプションに -force をつけて無理くりアプデするらしい。
また、パッケージが更新されてプログラムが動く保証はないので、ブランチを分けるなど、慎重にすること。
[疑問]audit fix では修正されない場合ってどういうとき???
[疑問]audit fix でアプデされるのはローカルのみ???
[疑問]audit fix -f でもアプデされないパッケージは???
脆弱性の警告を受けたnpmパッケージの依存関係を力技で直す
https://qiita.com/hibikikudo/items/0af352acac85fce28ec2
npmパッケージの脆弱性を自動チェックして対応する方法 – 2つの簡単な工夫を紹介
https://thilog.com/npm-security-check/
npm ci
ci npm ci
Install a project with a clean slate
Usage:
npm ci
Options:
[--no-audit] [--ignore-scripts] [--script-shell <script-shell>]
aliases: clean-install, ic, install-clean, isntall-clean
Run "npm help ci" for more info
clear install
npm install と似ているが、
- package-lock.json or npm-shrinkwrap.json が必須
- それらが package.json の記述と矛盾する場合、エラー
- 依存追加には使えない。(npm install xxx でやる)
- node_modules はいったん全消しされる
- npm installはpackage-lock.json を更新することがしばしばあるが、npm ci はpackage-lock.jsonに基づいてインストールするため、そういったことは起きない
https://ginpen.com/2019/12/04/npm-install-vs-ci/
npm install は package-lock.json を更新することがしばしばあります。
理由は package.json に記述する semver が幅のあるバージョンを許すためで、また package-lock.json は(”lock” という名前に反して)node_modules の実際を反映するものだからです。
npm dedupe
dedupe npm dedupe
Reduce duplication in the package tree
Usage:
npm dedupe
Options:
[--global-style] [--legacy-bundling] [--strict-peer-deps] [--no-package-lock]
[--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts]
[--no-audit] [--no-bin-links] [--no-fund] [--dry-run]
[-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]]
[-ws|--workspaces]
alias: ddp
Run "npm help dedupe" for more info
deduplication : 重複排除
パッケージの重複を無くす
シンプルにやるだけお得なんじゃね?
npm dedupeでモジュールの重複を解消する
https://qiita.com/totto357/items/585b6bb225021f723c5e
npm init
init npm init
Create a package.json file
Usage:
npm init [--force|-f|--yes|-y|--scope]
npm init <@scope> (same as `npx <@scope>/create`)
npm init [<@scope>/]<name> (same as `npx [<@scope>/]create-<name>`)
Options:
[-y|--yes] [-f|--force]
[-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]]
[-ws|--workspaces]
aliases: create, innit
Run "npm help init" for more info
initialize : 初期化
package.json が作成される。
npm init しないとどうなる?
https://qiita.com/sugurutakahashi12345/items/1049a33b86225f6345fe
npm install
install npm install
Install a package
Usage:
npm install [<@scope>/]<pkg>
npm install [<@scope>/]<pkg>@<tag>
npm install [<@scope>/]<pkg>@<version>
npm install [<@scope>/]<pkg>@<version range>
npm install <alias>@npm:<name>
npm install <folder>
npm install <tarball file>
npm install <tarball url>
npm install <git:// url>
npm install <github username>/<github project>
Options:
[-S|--save|--no-save|--save-prod|--save-dev|--save-optional|--save-peer]
[-E|--save-exact] [-g|--global] [--global-style] [--legacy-bundling]
[--strict-peer-deps] [--no-package-lock]
[--omit <dev|optional|peer> [--omit <dev|optional|peer> ...]] [--ignore-scripts]
[--no-audit] [--no-bin-links] [--no-fund] [--dry-run]
[-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]]
[-ws|--workspaces]
aliases: i, in, ins, inst, insta, instal, isnt, isnta, isntal, add
Run "npm help install" for more info
一番の大玉。
普通、installをすると、
- package.json のdependenciesに追記
- インストールするパッケージが用いているpackageをpackage-lock.json に記載
- node_modulesにパッケージをインストール
的な流れをする。
ここで、インストールの仕方にはいくつかり、
ローカルかグローバルか [-global]
ローカルは現在のプロジェクトでのみ使い、グローバルはプロジェクト間を超えて使えるようになる。
詳しくは下記
きちんとわかる、npm install 第1回
https://www.codegrid.net/articles/2020-npm-install-1/
dependenciesに記載するか [--save]
[--save]によって install する際にdependenciesにも記載する
が、今のバージョンではデフォルトで記載されるらしい
開発のときのみ使うパッケージか [--save-dev]
[--save-dev]によって、package.json の devDependencies欄 にパッケージ名が記録される。
リリースする際には不要なパッケージなどを記載する。
npm prefix
prefix npm prefix
Display prefix
Usage:
npm prefix [-g]
Options:
[-g|--global]
Run "npm help prefix" for more info
prefix : 接頭語
npm を実行する際のディレクトリを示す
結局のところ、npm prefix
は現在のディレクトリと等価
npm prefix -g
で、グローバルパッケージの所在わかる
npm prefix
と直接は関係ないが、prefixの使い方は下記参照
npm run command --prefix directory でサブディレクトリのコマンドを実行する。
https://blog.rhyztech.net/npm_prefix/
npm run-script
run-script npm run-script
Run arbitrary package scripts
Usage:
npm run-script <command> [-- <args>]
Options:
[-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]]
[-ws|--workspaces] [--if-present] [--ignore-scripts]
[--script-shell <script-shell>]
aliases: run, rum, urn
Run "npm help run-script" for more info
npm run の使われ方の方が多い。
config.json
のscripts
に書かれているコマンドを実行する
npm run <command>
のcommmandに、config.jsonに書かれているコマンドを記述する
npm uninstall
uninstall npm uninstall
Remove a package
Usage:
npm uninstall [<@scope>/]<pkg>...
Options:
[-S|--save|--no-save|--save-prod|--save-dev|--save-optional|--save-peer]
[-w|--workspace <workspace-name> [-w|--workspace <workspace-name> ...]]
[-ws|--workspaces]
aliases: un, unlink, remove, rm, r
Run "npm help uninstall" for more info
デフォルトでは、node_modulesからパッケージを消すだけ。
package.json
等にはリストに残っているので、再度npm install
をするとインストールされる。
--save
はDependenciesからの削除
--save-dev
はdevDependenciesからの削除
--g
はグローバルパッケージの削除
npmのuninstallコマンドを忘れがちなのでメモ
https://qiita.com/mamosan/items/6f1cf71ccd82216fe25b