【JavaScript】Knipを使用して不要なコードや依存関係を見つける

## Knipとは

Knipを使用すると未使用のファイルや依存関係、`export`などを検出できます。

https://knip.dev/

## 使い方

### インストール

以下の手順でインストールできます。

```shell
yarn add -D knip typescript @types/node
```
:::note info
`typescript`, `@types/node`はすでにインストールされていれば不要です。
:::

:::note warn
Yarnを使用してインストールした際に問題が発生した場合は[Yarnでインストールした際のエラーの対処法](#yarnでインストールした際のエラーの対処法)もご確認ください。
:::

`package.json`の`scripts`に`knip`を追加します。

```json:package.json
{

  "scripts": {
    "knip": "knip"
  },
  
}
```

以下のように実行できます。

```terminal
yarn knip
```

実行すると使用していないファイルなどが報告されます。

```terminal
$ yarn knip    
Unused files (9)
src/types/auth.ts
src/types/change-user-info-success.ts
src/types/validate-token-error.ts
src/utils/cookie/get-current-user-id.ts
src/utils/error/custom/current-user-id-error.ts
src/utils/error/custom/validation-error.ts
src/utils/error/handler/use-error-handler.ts
src/utils/type-guard/is-record.ts
src/utils/type-guard/is-string-array.ts
Unused dependencies (2)
@types/react-dom  package.json
react-dom         package.json
Unlisted binaries (3)
commitlint  lefthook.yml
eslint      lefthook.yml
eslint      package.json
Unused exported types (6)
SignUpFormValues             type  src/app/(auth)/sign-up/_components/sign-up-form/use-sign-up-form.ts:10:13
SnackbarsState               type  src/app/_components/snackbars/use-snackbars-store.ts:17:13               
KeyDownHandler               type  src/components/editable-text/use-editable-text.types.ts:20:13            
CheckboxProps                type  src/components/form-controls/checkbox/index.tsx:3:13                     
Props                        type  src/components/form-controls/text-area/index.tsx:4:13                    
ValidationErrorMessageProps  type  src/components/form-controls/validation-error-message/index.tsx:1:13
```

https://knip.dev/overview/getting-started

### 設定

設定は`knip.json`などに記述します。
使用可能なファイル名は以下のページで確認できます。

https://knip.dev/overview/configuration#location

誤検知などでファイルや依存関係などを無視したい場合には、設定ファイルに記述します。

```json:knip.json
{
  "$schema": "https://unpkg.com/knip@5/schema.json",
  "ignore": [".pnp.*"],
  "ignoreBinaries": [
    "commitlint",
  ],
  "ignoreDependencies": [
    "@types/react-dom",
    "react-dom",
  ]
}
```

設定項目の詳細や他の設定項目については以下のページをご確認ください。

https://knip.dev/reference/configuration

## Yarnでインストールした際のエラーの対処法

YarnでインストールしてKnipを実行した際に、以下のようなエラーが発生することがあります。

```terminal
$ yarn knip       
/home/node/project/.pnp.cjs:22095
      Error.captureStackTrace(firstError);
            ^

Error: @pnpm/npm-resolver tried to access @pnpm/logger (a peer dependency) but it isn't provided by its ancestors; this makes the require call ambiguous and unsound.

Required package: @pnpm/logger
Required by: @pnpm/npm-resolver@virtual:d26bd051d452c5c8434f4f36c293cb14d19393990244c1e879020a0dfe893af5d2b8a1f80d443c8367236743c22e878370388f92e2f43557662f6bd96c62909e#npm:18.1.1 (via /home/node/project/.yarn/__virtual__/@pnpm-npm-resolver-virtual-400fc2bc03/0/cache/@pnpm-npm-resolver-npm-18.1.1-fa132837df-6157882e65.zip/node_modules/@pnpm/npm-resolver/lib/)

Ancestor breaking the chain: @pnpm/workspace.pkgs-graph@npm:2.0.15


Require stack:
- /home/node/project/.yarn/__virtual__/@pnpm-npm-resolver-virtual-400fc2bc03/0/cache/@pnpm-npm-resolver-npm-18.1.1-fa132837df-6157882e65.zip/node_modules/@pnpm/npm-resolver/lib/pickPackage.js
- /home/node/project/.yarn/__virtual__/@pnpm-npm-resolver-virtual-400fc2bc03/0/cache/@pnpm-npm-resolver-npm-18.1.1-fa132837df-6157882e65.zip/node_modules/@pnpm/npm-resolver/lib/index.js
- /home/node/project/.yarn/cache/@pnpm-workspace.pkgs-graph-npm-2.0.15-d26bd051d4-f16cebedb0.zip/node_modules/@pnpm/workspace.pkgs-graph/lib/index.js
    at require$$0.Module._resolveFilename (/home/node/project/.pnp.cjs:22095:13)
    at require$$0.Module._load (/home/node/project/.pnp.cjs:21945:42)
    at Module.require (node:internal/modules/cjs/loader:1137:19)
    at require (node:internal/modules/helpers:121:18)
    at Object.<anonymous> (/home/node/project/.yarn/__virtual__/@pnpm-npm-resolver-virtual-400fc2bc03/0/cache/@pnpm-npm-resolver-npm-18.1.1-fa132837df-6157882e65.zip/node_modules/@pnpm/npm-resolver/lib/pickPackage.js:11:18)
    at Module._compile (node:internal/modules/cjs/loader:1255:14)
    at Module._extensions..js (node:internal/modules/cjs/loader:1309:10)
    at require$$0.Module._extensions..js (/home/node/project/.pnp.cjs:22139:33)
    at Module.load (node:internal/modules/cjs/loader:1113:32)
    at require$$0.Module._load (/home/node/project/.pnp.cjs:21976:14)

Node.js v20.2.0
```

`.yarnrc.yml`に以下を追記した後に`yarn install`することでエラーが解消します。

```yml:.yarnrc.yml
packageExtensions:
  '@pnpm/workspace.pkgs-graph@2.0.15':
    peerDependencies:
      '@pnpm/logger': '^5.0.0'
```

上記のように記述するとエラーが解消する理由は依存関係の不具合がなくなるからです。

ます、Knipが`@pnpm/workspace.pkgs-graph`に依存しています。

https://github.com/webpro/knip/blob/b8076a284982d61009dc83c68632044ef8ea873d/packages/knip/package.json#L61

そして`@pnpm/workspace.pkgs-graph`が`@pnpm/npm-resolver`に依存しています。

https://github.com/pnpm/pnpm/blob/9e6bbfb778056bfb0e23077f529075b536309355/workspace/pkgs-graph/package.json#L34

`@pnpm/npm-resolver`は`peerDependencies`に`"@pnpm/logger": "^5.0.0"`を記述しています。

https://github.com/pnpm/pnpm/blob/9e6bbfb778056bfb0e23077f529075b536309355/resolving/npm-resolver/package.json#L34

しかし、`@pnpm/workspace.pkgs-graph`では`dependencies`や`peerDependencies`に`@pnpm/logger`が記述されていません。

https://github.com/pnpm/pnpm/blob/9e6bbfb778056bfb0e23077f529075b536309355/workspace/pkgs-graph/package.json#L32

Knipは`"@pnpm/logger": "^5.0.0"`を`dependencies`に記述しています。

https://github.com/webpro/knip/blob/b8076a284982d61009dc83c68632044ef8ea873d/packages/knip/package.json#L60

よって、`@pnpm/workspace.pkgs-graph`の`peerDependencies`に`@pnpm/logger`を追加することで依存関係の不具合がなくなり、エラーが解消されます。


エラーの解消方法については以下の記事もご確認ください。

https://qiita.com/P-man_Brown/items/fa957cc361b6eb1bd58e