ひびのログ

日々ではないけどログを出力していくブログ

ESLint が一部設定されている JS + Vue.js プロジェクトに Prettier を導入しようとしてハマった

TL;DR

eslint-plugin-vue を導入してから Prettier を入れないと、変な風にフォーマットされることがあるよ。

f:id:tee-talog:20190529214634p:plain

背景

現在、古の JS コードをモダンな Webpack + Babel + Vue.js 環境に移行しています。
ビルドするディレクトリとしないディレクトリに分かれているイメージです。

そしてビルドするディレクトリで ESLint を実行しています。
入っているのは standard ルールだけ。
そしてプラグインに eslint-plugin-html が入っています。

Prettier を導入したい!

一応通常の JS や Vue.js コードは eslint-loader を通る設定になっており、ある程度の Lint はしてくれています。
しかし、fix をしていないため手動で修正する必要があります(歴史的な理由でしょうか……)。

そこで、fix を有効にした上で Prettier も導入してしまえば一石二鳥なのでは? と思い、早速設定していきました。





それが地獄の始まりとは知らずに……





……というのは完全に大げさですが。

導入方法

ESLint と Prettier を共存させる方法は 2 種類あります。
それぞれメリデメがあるので検討します。

1. Prettier を実行してから ESLint を実行

最終的に ESLint で fixable なルールは ESLint でフォーマットされるため、現在 ESLint が入っている状況では diff が少なくなります。

lint をするために Prettier の実行が必須になるため、エディタ上では正しく lint できない可能性があります。
(ESLint で Prettier でフォーマットされる部分のルールを無効化しておけば一応可能?)

2. ESLint と同時に Prettier を実行

原理としては、ESLint のプラグインとして Prettier 用のルールを追加し、ルールでエラーになり fix するタイミングでプラグインが Prettier にオプション付きでファイルを渡してあげる、という感じが近いかと思います。
Prettier の実行タイミングは ESLint の後です。
Prettier での整形がそのまま出るので、diff が多く出ます。きっと。

今回はこちらの設定を使用。そもそも Prettier の推奨がこちら。 というか 1 のほうは Webpack プラグインが Webpack 2 から更新されていない……

地獄

さて、実際にやってみました。
Prettier を導入してフォーマットしてみると、git diff に恐ろしい文字列が……

import axios from 'axios' import MyComponent from
'@/components/my-component.vue' const variable = 'variable' const func = (a, b)
 => { process(a, b) console.log('processing') return 'value' } //
コメントですこれはよくわからない処理です const wakaranaiFunc = () => { const wakaranai
 = 'wakaranai' return 'yappari-wakaranai' } export default { name:
'component-name', components: { MyComponent }, props: { prop1: { type: Array,
required: true },
:
:

※コードは例です





なんじゃこりゃぁあ!!!(松田優作並感)





Vue.js のコードがひどい整形をされています。このコードは動かないです。

これはひどい。

どうしてこうなった!

あくまで自分の推測です。

eslint-plugin-html が入っていることにより、.vue ファイルは HTML として認識されていました。
つまり、通常の HTML の中に <script> タグが存在、つまり JS とみなされて Lint がかかっていたのかと思います。

しかし、Prettier は <script> タグの中も HTML と認識し、無駄な改行を削除してしまったのでしょう。
80 文字制限に引っかからない限り改行しないように整形してしまいました。

ということかなーと。

Q.じゃあどうすれバインダー!

A.先に eslint-plugin-vue を入れてあげてください。そして plugins の html を削除して代わりに vue を設定してあげてください。

.vue がちゃんと Prettier でもフォーマットされるようになるのでこれで万事 OK だわ!

ちなみに plugin:vue/recommended を入れなかったら .vue がフォーマットされませんでした。

まとめ

Prettier と ESLint はプロジェクトの最初で導入しましょう。
それが無理なのであれば、必要な ESLint ルールを導入した後に Prettier を入れてあげるのがいいかもしれません。

プロジェクトによって運用等まちまちだと思うので、合うやり方の模索が必要です。

ESLint と Prettier を信じられるのであれば、ルール設定後 fix してしまってもいいのかもしれません。

参考

追記(2019/05/31)

こちらの webpack プラグインを使用すると、「Prettier を実行してから ESLint を実行」が楽にできました。

webpack の対象となっているファイルすべてがフォーマットされます。つまり CSS も webpack で読ませていた場合はそちらも対象となるので注意が必要です。

github.com