🧑‍🏫

package.json も lint する

2024/01/11に公開

はじめに

プロダクト開発において、ESLintStylelint をはじめとする linter は無くてはならないものになっています。

package.json においても、例えば以下のような決まり事を linter の恩恵によって担保できないか考え調べてみました。

  • scripts をアルファベット順に定義する
  • メジャーバージョンが 0 系であるパッケージは入れない
  • バージョンを固定してインストールする(~^ をつけない)

npm-package-json-lint

package.json 用の linter として npm-package-json-lint というものがありました。

https://github.com/tclindner/npm-package-json-lint

こちらを使うことで、上記決まり事を linter の恩恵によって担保できそうなので実際に導入してみます。

前提

今回は個人プロジェクトに導入してみます。現状の package.json は以下のようになっています。

https://github.com/TakaShinoda/portfolio_v4.0/blob/24ad9d182c0b456277eba6bab486eaf53af0d2be/package.json

インストール

プロジェクトにインストールします。

npm install --save-dev npm-package-json-lint

https://npmpackagejsonlint.org/docs/install

設定ファイルの作成

インストールしただけでは、まだ何もルールが有効になっていないので設定ファイルを作成します。

npmpackagejsonlint.config.js
const config = {
  // 後ほど記述
}

module.exports = config

https://npmpackagejsonlint.org/docs/configuration

scripts の定義

npm-package-json-lint を実行するための scriptspackage.json に定義します。

package.json
"scripts": {
  "lint:package": "npmPkgJsonLint ."
}

https://npmpackagejsonlint.org/docs/cli/

ルール

npm-package-json-lint をカスタマイズするためのルールは豊富にありますが、大きく分類すると以下の 8 つです。

  • Require node rules
  • Type rules
  • Valid value rules
  • Dependency rules
  • Scripts rules
  • Format rules
  • Package.json property rules
  • Disallowed node rules

それぞれの分類の中にさらにルールがあります。詳しくは以下を参照してください。

https://npmpackagejsonlint.org/docs/rules/

ルールの設定

冒頭で記述した決まりごとを担保するためには、以下のルールを設定すれば良さそうです。

  • Scripts rules
    • prefer-alphabetical-scripts
  • Dependency rules
    • prefer-no-version-zero-dependencies
    • prefer-no-version-zero-devDependencies
    • prefer-absolute-version-dependencies
    • prefer-absolute-version-devDependencies

scripts をアルファベット順に定義する

prefer-alphabetical-scripts を有効化することで、scripts がアルファベット順でない場合エラーにできます。

npmpackagejsonlint.config.js
const config = {
  rules: {
+   'prefer-alphabetical-scripts': 'error'
  }
}

module.exports = config

npm-package-json-lint を実行してみます。
現状の package.jsonscripts がアルファベット順でないためエラーになりました。

$ npm run lint:package

> lint:package
> npmPkgJsonLint .


./package.json
✖ prefer-alphabetical-scripts - node: scripts - Your scripts are not in alphabetical order. Please move dev after build.
1 error
0 warnings

scripts をアルファベット順に定義することでエラーはなくなりました。
https://github.com/TakaShinoda/portfolio_v4.0/pull/44/commits/66b400f24da7d04ae510e15626379f36d8fc1687

$ npm run lint:package

> lint:package
> npmPkgJsonLint .

https://npmpackagejsonlint.org/docs/rules/scripts/prefer-alphabetical-scripts/

メジャーバージョンが 0 系であるパッケージは入れない

prefer-no-version-zero-dependenciesprefer-no-version-zero-devDependencies を有効化することで、メジャーバージョンが 0 系であるパッケージがある場合エラーにできます。

npmpackagejsonlint.config.js
const config = {
  rules: {
    'prefer-alphabetical-scripts': 'error',
+   'prefer-no-version-zero-dependencies': 'error',
+   'prefer-no-version-zero-devDependencies': 'error'
  }
}

module.exports = config
$ npm run lint:package

> lint:package
> npmPkgJsonLint .


./package.json
✖ prefer-no-version-zero-dependencies - node: dependencies - You have invalid version 0 dependencies. Please use modules with a major version >= 1. Invalid dependencies include: next-themes, typesync
1 error
0 warnings

https://npmpackagejsonlint.org/docs/rules/dependencies/prefer-no-version-zero-dependencies/
https://npmpackagejsonlint.org/docs/rules/dependencies/prefer-no-version-zero-devdependencies/

バージョンを固定してインストールする(~^ をつけない)

prefer-absolute-version-dependenciesprefer-absolute-version-devDependencies を有効化することで、パッケージのバージョンに ~^ がある場合エラーにできます。

npmpackagejsonlint.config.js
const config = {
  rules: {
    'prefer-alphabetical-scripts': 'error',
    'prefer-no-version-zero-dependencies': 'error',
    'prefer-no-version-zero-devDependencies': 'error',
+   'prefer-absolute-version-dependencies': 'error',
+   'prefer-absolute-version-devDependencies': 'error'
  }
}

module.exports = config
$ npm run lint:package

> lint:package
> npmPkgJsonLint .


./package.json
✖ prefer-absolute-version-dependencies - node: dependencies - You are using an invalid version range. Please use absolute versions. Invalid dependencies include: @radix-ui/react-avatar, clsx, dayjs, iconoir-react, next, next-international, next-themes, tailwind-merge, typesync, vercel
✖ prefer-absolute-version-devDependencies - node: devDependencies - You are using an invalid version range. Please use absolute versions. Invalid devDependencies include: @testing-library/jest-dom, @testing-library/react, @types/fs-extra, @types/testing-library__jest-dom, autoprefixer, fs-extra, jest, jest-environment-jsdom, npm-package-json-lint, postcss, rss-parser, tailwindcss, ts-node
2 errors
0 warnings

https://npmpackagejsonlint.org/docs/rules/dependencies/prefer-absolute-version-dependencies/
https://npmpackagejsonlint.org/docs/rules/dependencies/prefer-absolute-version-devdependencies/

おわりに

npm-package-json-lint を用いることで、package.json においても linter の恩恵を受けることができることがわかりました。
ルールも豊富にあるので、それぞれのプロジェクトに応じた設定が柔軟にできそうだと思いました。
プロジェクト内の決まり事は、それを担保するために可能であれば仕組み化できると嬉しいなとあらためて思いました。

GitHubで編集を提案

Discussion