phpcsのおさらい その2: ルールセットの書き方、composerとGitHub Actions、Huskyの設定

こんにちは、みみです。

前回の続き、というかこちらが本筋のお話です。

いや分かるんです、私も最近は殆どJSばっかり書いているし、なんならコード書く量めっちゃ減ったし、PHPなんてお呼びじゃないっていう話も分かるんですが、ごく偶に書くからこそ間違えるんです、覚えないんです。そのためのlintなんです。自動化して楽をしましょう。一回設定したら楽になるから騙されたと思ってやってみましょう。

あとなんでそもそもそんな面倒くさいルール要るのと思うかも知れませんが、余計な諍いやエラーを未然に防ぐのです。もう怒りを抑えてそんなXXコードを一々レビューしたりしなくて良いの。GitHub Actions と Husky に任せようそれは。(ただし、phpcs disable を書いてたら開戦の合図ですね。)

私は基本一人で書いているから要らないっていう人は、半年後の自分のために設定するのです。私もほぼ一人で書いていることが多いです。私にとっては半年どころか1ヶ月前の自分も別人だよ…使ってなかった頃の自分のコードとかもう絶対見たくないよ🙈。

…というわけで本題に戻りましょう。

WordPress前提のお話ですし、勿論あくまで個人の見解ですので悪しからず。

5. カスタマイズしたルールセットの書き方

基本の規約はともかく、WordPressのPHPコード規約はちょっと毛色が違うというか、こんなのPHPじゃない!とお怒りの方もいらっしゃる?ことでしょう。

ですがWordPressの上にPHPを書くならば基本従った方が幸せになれると思います。自分の些細なコダワリや疑問より先達が協議して決めたルールの方が大抵深い考えに基づいており優れています。WordPressには大抵の人が把握していない長い歴史や知らない機能があるのです。特段の理由がないなら長いモノには巻かれるが吉です。いやいやそれは違うと思ったらPRを送ったら良いと思います。

…もしくはそっと除外することも可能です。

というわけでカスタマイズしたルールセットを適用していきましょう。

先ずチェックするべき公式ドキュメントとしてはこちらになります: Annotated Ruleset · squizlabs/PHP_CodeSniffer Wiki

以下では基本的にWordPressの開発環境を想定して書いています。

ルールセットのファイル名

私はphpcs.xml.dist っていう名前にWordPressとかでもなっているので単にマネッコして書いていたのですが、今回調べて、phpcs.xml、phpcs.xml、.phpcs.xml.dist、またはphpcs.xml.distだったら良い(phpcs を実行するディレクトリの中にあれば自動的に検索される)ということが分かりました。なるほど。
参照: https://github.com/WordPress/WordPress-Coding-Standards#using-a-custom-ruleset

書き方のサンプルは WordPress-Coding-Standards/phpcs.xml.dist.sample at develop · WordPress/WordPress-Coding-Standards にあります。

以下ではその内をいくつかピックアップして解説します。

prefixesの設定

WordPressのPHPコード規約には

変数、アクション/フィルター、および関数名には小文字を使用します(キャメルケースは使用しないでください)。アンダースコアで単語を区切ります。変数名を不必要に省略しないでください。

https://developer.wordpress.org/coding-standards/wordpress-coding-standards/php/#naming-conventions

というような命名規則があって、さらに、グローバルなものにはprefixを入れましょうと言われます。あんまり長い名前もまた可読性が落ちるのですが、特にWordPressの場合は他のプラグインとのバッティングを起こすと面倒くさいです。あと、色々混じってくると何由来のものか(自分さえ)わかりにくくなるので最初から独自の命名には独自のprefixを入れるという方法はベスト・プラクティスかなと思います。

公式ディレクトリに登録していなくてもココ守ってくれてると一目で分かりやすくて良いなーと個人的には思います。

そのprefixを指定するのが、

<rule ref="WordPress.NamingConventions.PrefixAllGlobals">
    <properties>
        <property name="prefixes" type="array">
            <element value="my_prefix"/>
        </property>
    </properties>
</rule>

の部分。my_prefix を好きな文字列に指定します。

I18nのdomain名

prefixと同じ様に、翻訳関数で使うドメイン名を指定できます。

<rule ref="WordPress.WP.I18n">
    <properties>
        <property name="text_domain" type="array">
            <element value="my-textdomain"/>
            <element value="library-textdomain"/>
        </property>
    </properties>
</rule>

色つけたりも出来るよ

あと私が個人的に入れるのは以下の2つ。

<!-- 出力に色を適用 -->
<arg name="colors" />

<!-- オプション p:進捗表示  s:エラー表示時にルールを表示 -->
<arg value="ps" />

適用するディレクトリ指定したり、外したりも勿論できます。<exclude-pattern>/vendor/*</exclude-pattern>とかです。

ルールの除外

先ずは取り敢えずルールに沿って書いておけばOK

しつこいようですが導入したての方にお伝えしたいのは、先達の知恵が詰まったコード規約、え?なんで?と思っても取り敢えず従って書いてみるのが吉です。安易な考えで外さない方が良いです。何のためにphpcsしているのか分からなくなりますので。

他のlinter同様、一行に限って除外したり出来るdisableやignoreも用意されていますが、除外することを考える前に、自分の設計を疑いましょう。其のためのlintです。

慣れてきたらどうしても合わないルールを除外しても良いかも

上記を踏まえていただいた上で、別に公式ディレクトリに登録しようとしているわけでなければ、公式のルールにがっつり縛られる必要は全くありません。そのチーム、プロジェクト内で共通のルールが守られていれば基本構わないはずなので。

例えば、これはSquizの規約ですが、やっぱり、.が無いと一々怒られるとかは、ちょっと日本語圏で日本語コメントばりばりなプロジェクトだと微妙だなあ、とかはあると思います。私としては、コメントの内容の再チェックとしてまあ良いかなとも思うのですが、errorじゃなくてwarningぐらいにしてくれないかなーとかは思ったりもします。

配列はもう[]で良いだろ、というのは分からなくもないので、除外している人も多いかもしれないですね。

そういったローカルルールにそぐわないぞ、というルールをチームで相談して、除外しておけます。(逆に言うと、上記にあるような変数名にちゃんと接頭詞つけるとか、WordPressの変数名上書きしない、出力は全てエスケープする、とかはローカルルールとはいえWordPressとかセキュリティとか完全理解していると豪語出来る人以外は破らないほうが良いのかなあと。何のためにphpcsしてるのか分からなくなります。大事なことなので何度でもいいます。)

コメント末尾に.なんて一々書いていられるかという方は
<exclude name="Squiz.Commenting.InlineComment.InvalidEndChar"/>

やっぱりarray()は[]で書きたい方は
<exclude name="Generic.Arrays.DisallowShortArraySyntax.Found"/>

という感じで色々と設定ができます。

今回調べてやっと気が付いたのですが、array()で怒るのって Generic なんですね。

独自のルールセットを読み込ませるには

これらのルールセットをphpcsに読み込ませるには、該当のリポジトリルートか、phpcsを走らせるディレクトリに置けば良いはず、です。明示して指定するのは --standardオプションで、

$ phpcs --standard=/path/to/custom_ruleset.xml test.php

みたいに指定します。

6. composer.jsonを書いてリポジトリ毎に設定しておく

次はこれをリポジトリ毎に設定する方法です。composerを使います。composerは他にもtestとか外部ライブラリ読み込ませたりとかものすごく色々出来るお利口さんなのですが、私は普段はほぼphpcs目的でしか使っていません。すいませんすいません大分と宝の持ち腐れ感は日々感じています。

composerの設定は、composer.json に書きます。お作法がまだイマイチ分かってないですが、phpcs使うだけなら多分こういうのでいいはず。間違ってたらそっと叱ってください。

{
  "name": "as-you-like-name",
  "description": "As You Like Description",
  "license": "GPL-2.0-or-later",
  "require-dev": {
    "squizlabs/php_codesniffer": "*",
    "dealerdirect/phpcodesniffer-composer-installer": "*",
    "phpcompatibility/phpcompatibility-wp": "*",
    "wp-coding-standards/wpcs": "*"
  },
  "scripts": {
    "format": "phpcbf --standard=./.phpcs.xml.dist --report-summary --report-source",
    "lint": "phpcs"
  }
}

これを上記の独自のルールセットを書いたファイルと一緒にリポジトリのトップに入れておいて、composer installします。あとはそのリポジトリでcomposer phpcsすればOK。リポジトリごとのルールセットが反映され、各々の開発環境での差異が無くなります

リポジトリにnpm を使っていれば、"lint:php": "composer format && composer lint" とか書いておくと、npm run lint:php で自動整形とチェックが走ってくれます。

7. husky を設定して守ってもらう

huskyについては先ず、リントに便利な、開発者ツール「 husky 」🐶を使おう! | 株式会社ベクトルを見てください。

pre-commitnpm run lint:php かそれを含むスクリプトを指定したら、ちゃんと規約エラーをクリアしていないとhuskyが怒ってくれて無駄なコミットを防ぎます。自分のミスも皆のミスも未然に防いでくれるお利口さんです。

3ヶ月ぶりに触るリポジトリとかで、忘れがちでしょコミット前のlintなんて。まだ使ったことが無い方はマジで入れたほうが幸せになるから今すぐ導入しましょう。

名前からして天才の仕業ですよね。ハスキーがずっと守ってくれてると思うとキュンとする。

8. GitHub Actions を設定して守ってもらう

もうちょっと疲れてきたしActionsは分かる人だけ分かれば良いので走り書きにします。

この辺使ったらできます(雑)。
PHP_CodeSniffer Check with Annotations · Actions · GitHub Marketplace

アレ見たことある人ぽいなあと思ったらDominikさんがコントリビューターだった。

PR来たら回るようにしておきましょう。Husky切ってまでコミットしてくる狂人には中々出会えないとは思うのですが、どんなミスが起きるか分からないのでダブルで設定しておくと安心して夜もぐっすり眠れます。

.editorconfig もついでに設定しておこう

その他.editorconfig という主にプログラミング言語向けの、テキストファイルのレイアウトを統一するための設定ファイルもあります。合わせて設定しておくとさらに幸せになれるかもしれません。

WordPress向けにはこんな感じ。
wordpress-develop/.editorconfig at master · WordPress/wordpress-develop


…果たして、この記事が刺さる人は居るのだろうか。全然関係ないけど、huskyの画像検索が楽しくて不必要に多用しましたが後悔は無いです。

というわけで、2021年も正しく楽して開発しませう!

この記事を書いた人