PHPStan がめちゃくちゃ遅い場合

この記事は最終更新日から 1年以上 が経過しています。

最近、WSL 2 上で PHPStan がめちゃくちゃ遅くて困っていたのですが、 なんとか重い腰を上げて調査をし、高速化する方法を見つけたのでここにメモしておきます。 というかこの方法は、高速化する方法というよりは、遅くならない方法と言った方が正しいのかもしれません。 ググっても出てこなかったのでレアケースなのかもしれませんが、PHPStan が遅くて遅くて困っている方は参考にしてみてください。

現象と原因

現象としては、WSL 2 上で PHPStan を動かすと、処理時間が数分以上かかってしまい WSL 2 がフリーズ状態になってしまうというものです。 VS Code で WSL 拡張機能を使用して接続している場合、PHPStan の実行が遅すぎるために、VS Code と WSL 2 との間の接続が切れてしまいます。 待ってれば返ってくるのなら良いのですが、最悪のパターンだと WSL 2 を強制的に再起動させないといけなくなってしまいます。

原因

いろいろと調査した結果、どうやら PHPStan がマルチスレッドで動作していることが原因と判明。 そういえば以前はこんなに遅くなかったはずで、遅くなったのは PHPStan がバージョンアップしてからだなと思い出しました。 最新の PHPStan ではマルチスレッドによる並列処理はデフォルトで有効になっています。 CPU のコアがたくさんあるような高スペックなマシンであれば、 マルチスレッドで処理速度が早くなるのかもしれませんが、 低スペックなマシンの場合は、各スレッドが CPU やメモリなどのマシンリソースを奪い合ってしまい、 どのスレッドも処理を完了させることができなくなってしまって逆に遅くなってしまうのです。

動いてはいるが遅すぎてほぼほぼフリーズ状態になっているように見えると言った方が正しい感じでしょうか。 PHPStan がマシンリソースを大量に使用してしまうために、 PHPStan 以外の他のプロセスもリソースが足りなくなってしまい、 その結果、何もできない状況に陥ってしまって、WSL 2 の再起動が必要になってしまうと。

マルチスレッドによる並列処理が早いのは、高スペックなマシンで CPU やメモリなどのリソースに余裕がある場合のみです。 低スペックなマシンでリソースが貧弱な状況であれば、シングルスレッドで直列処理した方が早いのです。 なんでもかんでも並列処理にすれば良いってものじゃないってことですね。

loadaverage.png

解決方法

ということで原因はマルチスレッドで並列処理されていることなので、 マルチスレッドを無効化してシングルスレッド化して直列処理させます。 なお、高スペックのマシンであればデフォルトのマルチスレッドの状態の方が早いかもしれませんので注意してください。 低スペックのマシンであれば、おそらくシングルスレッドの方が早いです。 ご自身の環境に合わせて設定しましょう。 マルチスレッドを無効化してシングルスレッドにすれば、少なくともリソース不足でフリーズすることはなくなります。

マルチスレッドを無効化する方法は主に2つあります。

--debug オプションを使用する

1つ目の方法は PHPStan の実行時に --debug オプションを使用する方法です。 --debug オプションを使用すると、下記のような影響があります。

  • マルチスレッドが無効になる
  • キャッシュが効かなくなる
  • プログレスバーの代わりに処理中のファイルの一覧が表示される
  • 最初のエラーで処理が停止する

--debug オプションを使用すると、マルチスレッドを無効化することができますが、 副作用としてキャッシュが効かなくなりますので、後述の2つ目の方法を使用した方が良いでしょう。 どのファイルが処理されているか確認したい場合や、動作確認をしたい場合は、こちらの方法の方が便利かもしれません。

phpstan analyse --debug

設定ファイルで指定する

2つ目の方法は、PHPStan の設定ファイル phpstan.neon で parallelmaximumNumberOfProcesses を設定する方法です。 値を 1 に設定するとマルチスレッドが無効になります。 こちらの方法であれば、キャッシュを有効なままにしておけるのでオススメです。

phpstan.neon
parameters:
	parallel:
		maximumNumberOfProcesses: 1

参考サイト

関連記事

PHP のコードを実行する前に、バグがあるかどうか調べられると便利だとは思いませんか?PHP はスクリプト言語ですので、いくら文法的に正しいコードであっても、実際に実行させるまでバグか発生するかどうかわからないという、スクリプト言語であるが故の本質的な問題を抱えています。C や Java など他のコンパイル言語ではコン ...
Windows 上の Docker を高速化するためには WSL 2 を使うと良いというのは、以前の記事「Windows の Docker 環境を高速化する方法」で書きました。WSL 2 にファイルを置くと Docker が早くなるのは良いのですが、それに起因して別の問題が発生します。その WSL 2 に置いたファイル ...
Docker は、構成を気軽に組み替えたりできるので、とても便利ですよね。Windows で Docker を使って開発している方も多いと思うのですが、個人的にはどうしても気が乗らない理由がありました。それは処理速度です。遅い。遅すぎる。めちゃくちゃ遅い。つらい。耐えられない。。。ということで調査しました。いろいろと調 ...
Windows で開発している際、動作確認のために Linux のプログラムやコマンドを動かしたいなと思うことがあります。そんな場合に便利なのが WSL(Windows Subsystem for Linux)です。WSL(Windows Subsystem for Linux)とは?WSL(Windows Subsy ...

記事検索

最新記事

人気記事

RSSフィード

お知らせ

フィードバック

要望などあれば、お気軽にどーぞ。 不具合やバグを発見した場合も、連絡をいただけると助かります。

匿名でフィードバックする
匿名でフィードバックする

要望などあれば、お気軽にどーぞ。 不具合やバグを発見した場合も、連絡をいただけると助かります。

なお、このフォームから入力された内容について、管理者から返信はできませんので注意してください。 もし、管理者からの返信が必要であれば、X(Twitter) もしくは、お問い合わせより、お願いします。

  • フィードバックの送信が完了しました。