Vite + Vue3で爆速開発のための準備の準備 #2 (eslint, Prettierを導入する)
こちらの続きです。
開始時点のソースコードは以下にある。
このスクラップではeslintやpretterなど、静的コード解析ツール(eslint)とコードの整形ツール(Prettier)を導入する。
なぜ入れるのか
現時点での私見です。
ESLint
- 共通のルールのもとコーディングを行うことができ一定の品質を保つことができる(保っていることが言える)
- ESLintのルール内でコードは書かれているため、チェックされる範囲でのバグがないことが保証される
- 構文レベルでバグになるもの(なりそうなもの)をいち早く検知することができる
- バグの発生件数が減る。
- (個人的に)手戻りは萎えるので早め早めに検知しくれることはこの手戻りのステップを減少させてくれるので開発体験的にもよいものになる。(単体テストでも似たようなことが言える)
- PRレビューで変更に対しての確認に集中することができる
- 他の理由とほとんど重なっていますがESLintのルール内で書かれているので
Prettier
- 個々人の勝手なルールでコードの整形を行わず統一することができる
- ソースコードの見た目は「きれい」に保ちたいもの(もちろん中身もだけど)その「きれい」の基準をツール上で決めて自動で全体に適用させることができる
- PRレビューで変更に対しての確認に集中することができる
- ESLintでも同じこと書いていますが、ツールでチェック・直してくれるところは直してもらい本来の目的に注力することでレビューの質、コードの質を上げることが期待される。
もちろんこれをいれただけでは守られているかの保証はできない(ツールを使うかどうかが個人の勝手になってしまう)のでコードの変更時にチェック・整形が自動的に行われるようにすることは必要になる。
しかし、そもそもツールをいれないことには話にならないので兎にも角にも導入する。
ESLintの導入
eslintをインストール
eslintの初期設定をしてくれるコマンドが用意されているのでそれを呼び出します。
$ npm init @eslint/config
以下のように質問に答えると初期設定 + installを行ってくれる
質問に答える
$ npm init @eslint/config
✔ How would you like to use ESLint? · style
✔ What type of modules does your project use? · esm
✔ Which framework does your project use? · vue
✔ Does your project use TypeScript? · No / Yes
✔ Where does your code run? · browser
✔ How would you like to define a style for your project? · guide
✔ Which style guide do you want to follow? · standard-with-typescript
✔ What format do you want your config file to be in? · YAML
Checking peerDependencies of eslint-config-standard-with-typescript@latest
The config that you've selected requires the following dependencies:
eslint-plugin-vue@latest eslint-config-standard-with-typescript@latest @typescript-eslint/eslint-plugin@^5.0.0 eslint@^8.0.1 eslint-plugin-import@^2.25.2 eslint-plugin-n@^15.0.0 eslint-plugin-promise@^6.0.0 typescript@*
✔ Would you like to install them now? · No / Yes
✔ Which package manager do you want to use? · npm
Installing eslint-plugin-vue@latest, eslint-config-standard-with-typescript@latest, @typescript-eslint/eslint-plugin@^5.0.0, eslint@^8.0.1, eslint-plugin-import@^2.25.2, eslint-plugin-n@^15.0.0, eslint-plugin-promise@^6.0.0, typescript@*
added 77 packages, and audited 244 packages in 5s
79 packages are looking for funding
run `npm fund` for details
found 0 vulnerabilities
Successfully created .eslintrc.yml file in /Users/satjopg/development/satjopg/git/sample-vite-vue3-app
yamlファイルの中身は以下の通り
特に触れる点はなさそう。
yamlの中身
env:
browser: true
es2021: true
extends:
- plugin:vue/vue3-essential
- standard-with-typescript
overrides: []
parserOptions:
ecmaVersion: latest
sourceType: module
plugins: - vue
rules: {}
ESLintのルールに基づいてVSCodeの拡張をいれて設定
{
"eslint.validate": ["html", "javascriptreact", "typescriptreact", "vue"]
}
ESLintを実行するためのコマンドを追加
{
scripts: {
+ "lint": "eslint --ext .vue,.ts src/"
}
}
実行する....怒られた
$ npm run lint
Oops! Something went wrong! :(
ESLint: 8.23.0
Error: Error while loading rule '@typescript-eslint/dot-notation': You have used a rule which requires parserServices to be generated. You must therefore provide a value for the "parserOptions.project" property for @typescript-eslint/parser.
Occurred while linting /Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/main.ts
at getParserServices (/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/@typescript-eslint/utils/dist/eslint-utils/getParserServices.js:22:15)
at create (/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/@typescript-eslint/eslint-plugin/dist/rules/dot-notation.js:85:81)
at Object.create (/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/@typescript-eslint/utils/dist/eslint-utils/RuleCreator.js:41:20)
at createRuleListeners (/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/eslint/lib/linter/linter.js:922:21)
at /Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/eslint/lib/linter/linter.js:1104:110
at Array.forEach (<anonymous>)
at runRules (/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/eslint/lib/linter/linter.js:1041:34)
at Linter._verifyWithoutProcessors (/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/eslint/lib/linter/linter.js:1393:31)
at Linter._verifyWithConfigArray (/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/eslint/lib/linter/linter.js:1762:21)
at Linter.verify (/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/node_modules/eslint/lib/linter/linter.js:1475:65)
公式ドキュメントや記事(本当にありがとうございます)を参考に設定を追加する
projectの追加については以下に記載されている
$ npm i -D @typescript-eslint/parser
env:
browser: true
es2021: true
extends:
- plugin:vue/vue3-essential
- standard-with-typescript
overrides: []
+ parser: 'vue-eslint-parser'
parserOptions:
+ parser: '@typescript-eslint/parser'
ecmaVersion: latest
sourceType: module
+ project: './tsconfig.json'
+ extraFileExtensions: ['.vue']
plugins:
- vue
rules: {}
いざ実行
$ npm run lint
> sample-vite-vue3-app@0.0.0 lint
> eslint --ext .vue,.ts src/
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/App.vue
0:0 error Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: src/App.vue.
The extension for the file (.vue) is non-standard. You should add "parserOptions.extraFileExtensions" to your config
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/components/HelloWorld.vue
0:0 error Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: src/components/HelloWorld.vue.
The extension for the file (.vue) is non-standard. You should add "parserOptions.extraFileExtensions" to your config
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/main.ts
5:1 error More than 1 blank line not allowed no-multiple-empty-lines
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/pages/Login.vue
0:0 error Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: src/pages/Login.vue.
The extension for the file (.vue) is non-standard. You should add "parserOptions.extraFileExtensions" to your config
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/pages/Top.vue
0:0 error Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: src/pages/Top.vue.
The extension for the file (.vue) is non-standard. You should add "parserOptions.extraFileExtensions" to your config
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/router/index.ts
1:60 error Extra semicolon @typescript-eslint/semi
8:50 error Extra semicolon @typescript-eslint/semi
10:17 error Extra semicolon @typescript-eslint/semi
17:54 error Extra semicolon @typescript-eslint/semi
18:19 error Extra semicolon @typescript-eslint/semi
21:2 error Extra semicolon @typescript-eslint/semi
26:3 error Extra semicolon @typescript-eslint/semi
31:3 error Extra semicolon @typescript-eslint/semi
33:22 error Extra semicolon @typescript-eslint/semi
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/vite-env.d.ts
1:1 error Do not use a triple slash reference for vite/client, use `import` style instead @typescript-eslint/triple-slash-reference
✖ 15 problems (15 errors, 0 warnings)
10 errors and 0 warnings potentially fixable with the `--fix` option.
しっかり怒られた。
vueファイルの箇所パースできないで怒られていた....
自動で直してくれるところは自動で直してもらいましょう
{
scripts: {
"lint:fix": "npm run lint -- --fix"
}
}
実行。減りましたのでこれを直していく。
npm run lint:fix chapter/#2 ✗
> sample-vite-vue3-app@0.0.0 lint:fix
> npm run lint -- --fix
> sample-vite-vue3-app@0.0.0 lint
> eslint --ext .vue,.ts src/
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/App.vue
0:0 error Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: src/App.vue.
The extension for the file (.vue) is non-standard. You should add "parserOptions.extraFileExtensions" to your config
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/components/HelloWorld.vue
0:0 error Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: src/components/HelloWorld.vue.
The extension for the file (.vue) is non-standard. You should add "parserOptions.extraFileExtensions" to your config
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/pages/Login.vue
0:0 error Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: src/pages/Login.vue.
The extension for the file (.vue) is non-standard. You should add "parserOptions.extraFileExtensions" to your config
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/pages/Top.vue
0:0 error Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: src/pages/Top.vue.
The extension for the file (.vue) is non-standard. You should add "parserOptions.extraFileExtensions" to your config
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/vite-env.d.ts
1:1 error Do not use a triple slash reference for vite/client, use `import` style instead @typescript-eslint/triple-slash-reference
✖ 5 problems (5 errors, 0 warnings)
vueファイルパースできないで怒られていたので直す。
よく見たら答えは書いてありました。
env:
browser: true
es2021: true
extends:
- plugin:vue/vue3-essential
- standard-with-typescript
overrides: []
parser: 'vue-eslint-parser'
parserOptions:
parser: '@typescript-eslint/parser'
ecmaVersion: latest
sourceType: module
project: './tsconfig.json'
+ extraFileExtensions: ['.vue']
plugins:
- vue
rules: {}
実行、エラー内容が見れました。
npm run lint:fix chapter/#2 ✗
> sample-vite-vue3-app@0.0.0 lint:fix
> npm run lint -- --fix
> sample-vite-vue3-app@0.0.0 lint
> eslint --ext .vue,.ts src/
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/pages/Login.vue
1:1 error Component name "Login" should always be multi-word vue/multi-word-component-names
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/pages/Top.vue
1:1 error Component name "Top" should always be multi-word vue/multi-word-component-names
/Users/satjopg/development/satjopg/git/sample-vite-vue3-app/src/vite-env.d.ts
1:1 error Do not use a triple slash reference for vite/client, use `import` style instead @typescript-eslint/triple-slash-reference
✖ 3 problems (3 errors, 0 warnings)
最初の設定更新の投稿も直しておいた。
importに変えろと怒られていたけど、そのimportされたものを明示して使う箇所がなく
泣く泣く例外にした。
+ // eslint-disable-next-line @typescript-eslint/triple-slash-reference
/// <reference types="vite/client" />
ほかはComponentの命名はマルチワードにせよ、ということなので
pages配下のコンポーネントはXXXXPage.vue
に変更。
routerのimport箇所を直す (自動で直してくれなかったので)
const routes = [
{
path: '/',
name: 'top',
component: async () => {
- const top = await import('@/pages/Top.vue')
+ const top = await import('@/pages/TopPage.vue')
return top
}
},
{
path: '/login',
name: 'login',
component: async () => {
- const login = await import('@/pages/Login.vue')
+ const login = await import('@/pages/LoginPage.vue')
return login
}
}
]
再実行, 問題なくなる。
$ npm run lint
> sample-vite-vue3-app@0.0.0 lint
> eslint --ext .vue,.ts src/
(何も出力されない)
prettierをいれる
$ npm install -D prettier @vue/eslint-config-prettier
.prettierc
を設定する
ここはプロジェクトごとに設定すれば良いのでとりあえず。
{
// 1行120文字まで
"printWidth": 120,
// tabは空白2つ分
"tabWidth": 2,
// 文字列はシングルクウォートにする
"singleQuote": true,
// 末尾のカンマは設定しない
"trailingComma": "none",
// 行末はセミコロン
"semi": true
}
package.json
に実行用コマンドを追加し実行
{
"scripts": {
"format": "prettier -w src/*.{ts,vue} && prettier -w src/**/*.{ts,vue}"
}
}
$ npm run format
> sample-vite-vue3-app@0.0.0 format
> prettier -w src/*.{ts,vue} && prettier -w src/**/*.{ts,vue}
src/main.ts 171ms
src/vite-env.d.ts 5ms
src/App.vue 14ms
src/router/index.ts 178ms
src/components/HelloWorld.vue 55ms
src/pages/LoginPage.vue 6ms
src/pages/TopPage.vue 2ms
これにて導入完了
VSCodeの設定を追加して自動でフォーマットされるようにする
こちらの記事を参考にさせていただきました!
とてもわかりやすかったです、ありがとうございます!
{
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true
},
"[vue]": {
"editor.defaultFormatter": "dbaeumer.vscode-eslint"
},
"[javascript]": {
"editor.defaultFormatter": "dbaeumer.vscode-eslint"
},
"[typescript]": {
"editor.defaultFormatter": "dbaeumer.vscode-eslint"
},
"editor.formatOnSave": true
}
保存時に整形されるようになりました。
ここまでのコードは以下にコミット済み