CodeIgniter DevKit で php-cs-fixer を使いコーディングスタイルを修正する

この記事は CodeIgniter Advent Calendar 2022 - Qiita の19日目です。まだ、空きがありますので、興味のある方は気軽に参加してください。

CodeIgniter DevKit とは?

CodeIgniterのライブラリとプロジェクトのための開発用のツールキットです。

以下のツール(主なもの)が含まれています。

  • php-cs-fixer (CodeIgniter4のコーディング標準)
  • PHPStan
  • Psalm
  • Deptrac
  • Infection
  • Rector

DevKit のインストール

Composerからインストールします。

minimum-stabilitydev に変更します。

$ composer config minimum-stability dev
phpstan/extension-installer contains a Composer plugin which is currently not in your allow-plugins config. See https://getcomposer.org/allow-plugins
Do you trust "phpstan/extension-installer" to execute code and wish to enable it now? (writes "allow-plugins" to composer.json) [y,n,d,?] y

prefer-stabletrue に変更します。

$ composer config prefer-stable true

(2022-12-21 追記) DevKit v1.1.0 が少し古くなっていたため、インストールするバージョンを dev-develop に変更しました。

インストールします。

$ composer require --dev codeigniter4/devkit:dev-develop
./composer.json has been updated
Running composer update codeigniter4/devkit
Loading composer repositories with package information
Info from https://repo.packagist.org: #StandWithUkraine
Updating dependencies
Lock file operations: 51 installs, 0 updates, 0 removals
  - Locking amphp/amp (v2.6.2)
  - Locking amphp/byte-stream (v1.8.1)
  - Locking codeigniter/coding-standard (v1.7.0)
  - Locking codeigniter4/devkit (dev-develop c4726ff)
  - Locking composer/package-versions-deprecated (1.11.99.5)
  - Locking composer/pcre (3.1.0)
  - Locking composer/semver (3.3.2)
  - Locking composer/xdebug-handler (3.0.3)
  - Locking dnoegel/php-xdg-base-dir (v0.1.1)
  - Locking doctrine/annotations (1.14.2)
  - Locking doctrine/deprecations (v1.0.0)
  - Locking doctrine/lexer (2.1.0)
  - Locking fakerphp/faker (v1.21.0)
  - Locking felixfbecker/advanced-json-rpc (v3.2.1)
  - Locking felixfbecker/language-server-protocol (v1.5.2)
  - Locking fidry/cpu-core-counter (0.4.1)
  - Locking friendsofphp/php-cs-fixer (v3.13.1)
  - Locking netresearch/jsonmapper (v4.1.0)
  - Locking nexusphp/cs-config (v3.8.0)
  - Locking nexusphp/tachycardia (v1.4.0)
  - Locking phpdocumentor/reflection-common (2.2.0)
  - Locking phpdocumentor/reflection-docblock (5.3.0)
  - Locking phpdocumentor/type-resolver (1.6.2)
  - Locking phpstan/extension-installer (1.2.0)
  - Locking phpstan/phpstan (1.9.4)
  - Locking phpstan/phpstan-deprecation-rules (1.1.1)
  - Locking phpstan/phpstan-phpunit (1.3.2)
  - Locking psr/cache (3.0.0)
  - Locking psr/container (2.0.2)
  - Locking psr/event-dispatcher (1.0.0)
  - Locking roave/security-advisories (dev-latest ae56b09)
  - Locking spatie/array-to-xml (2.17.0)
  - Locking symfony/console (v6.2.2)
  - Locking symfony/deprecation-contracts (v3.2.0)
  - Locking symfony/event-dispatcher (v6.2.2)
  - Locking symfony/event-dispatcher-contracts (v3.2.0)
  - Locking symfony/filesystem (v6.2.0)
  - Locking symfony/finder (v6.2.0)
  - Locking symfony/options-resolver (v6.2.0)
  - Locking symfony/polyfill-ctype (v1.27.0)
  - Locking symfony/polyfill-intl-grapheme (v1.27.0)
  - Locking symfony/polyfill-intl-normalizer (v1.27.0)
  - Locking symfony/polyfill-mbstring (v1.27.0)
  - Locking symfony/polyfill-php80 (v1.27.0)
  - Locking symfony/polyfill-php81 (v1.27.0)
  - Locking symfony/process (v6.2.0)
  - Locking symfony/service-contracts (v3.2.0)
  - Locking symfony/stopwatch (v6.2.0)
  - Locking symfony/string (v6.2.2)
  - Locking vimeo/psalm (5.4.0)
  - Locking webmozart/assert (1.11.0)
Writing lock file
Installing dependencies from lock file (including require-dev)
Package operations: 2 installs, 3 updates, 3 removals
  - Downloading codeigniter4/devkit (dev-develop c4726ff)
  - Removing webmozart/path-util (2.3.0)
  - Removing rector/rector (0.15.1)
  - Removing openlss/lib-array2xml (1.0.0)
  - Installing spatie/array-to-xml (2.17.0): Extracting archive
  - Installing fidry/cpu-core-counter (0.4.1): Extracting archive
  - Upgrading vimeo/psalm (4.30.0 => 5.4.0): Extracting archive
  - Downgrading phpunit/php-code-coverage (9.2.22 => 9.2.21): Extracting archive
  - Upgrading codeigniter4/devkit (v1.1.0 => dev-develop c4726ff): Extracting archive
6 package suggestions were added by new dependencies, use `composer suggest` to see details.
Generating autoload files
composer/package-versions-deprecated: Generating version class...
composer/package-versions-deprecated: ...done generating version class
58 packages you are using are looking for funding.
Use the `composer fund` command to find out more!
phpstan/extension-installer: Extensions installed
infection/extension-installer: No extensions found
Generating autoload files
composer/package-versions-deprecated: Generating version class...
composer/package-versions-deprecated: ...done generating version class
Generated autoload files
No security vulnerability advisories found

インストールされました。

インストールしただけでは特に何も動きません。

vendor/codeigniter4/devkit/src/Template 以下に設定ファイルのテンプレートがあるので、 それをプロジェクトにコピーして設定を調整します。

php-cs-fixer の設定

それでは、php-cs-fixer の設定をします。

vendor/codeigniter4/devkit/src/Template/.php-cs-fixer.dist.php をプロジェクトルートにコピーします。

そして、コピーした .php-cs-fixer.dist.php をプロジェクトに合わせて調整します。

<?php

declare(strict_types=1);

use CodeIgniter\CodingStandard\CodeIgniter4;
use Nexus\CsConfig\Factory;
use PhpCsFixer\Finder;

$finder = Finder::create()
    ->files()
    ->in([
        __DIR__ . '/app/',
        __DIR__ . '/tests/',
    ])
    ->exclude([
        'build',
        'Views',
    ])
    ->append([
        __FILE__,
        __DIR__ . '/rector.php',
    ]);

$overrides = [
    'declare_strict_types' => true,
    'void_return'          => true,
];

$options = [
    'finder'    => $finder,
    'cacheFile' => 'build/.php-cs-fixer.cache',
];

return Factory::create(new CodeIgniter4(), $overrides, $options)->forProjects();

ここでは、上記のようにしました。

なお、php-cs-fixer の設定については、 https://mlocati.github.io/php-cs-fixer-configurator/ を見るとわかります。 気に入らない設定があれば、$overrides に設定して変更してください。

CodeIgniter4の設定については、 https://github.com/CodeIgniter/coding-standard/blob/master/src/CodeIgniter4.php で確認できます。

composer.json の設定

実行するためのコマンドを composer.json に追加します。

--- a/composer.json
+++ b/composer.json
@@ -23,7 +23,10 @@
        "test": "phpunit",
        "post-update-cmd": [
            "@composer dump-autoload"
-       ]
+       ],
+       "cs": "php-cs-fixer fix --ansi --verbose --dry-run --diff",
+       "cs-fix": "php-cs-fixer fix --ansi --verbose --diff --using-cache=yes",
+       "style": "@cs-fix"
    },
    "support": {
        "forum": "http://forum.codeigniter.com/",

これで、composer cs-fix でソースコードのコーディングスタイルが修正されます。

コーディングスタイルの修正

それではコーディングスタイルを修正してみましょう。

$ composer cs-fix
> php-cs-fixer fix --ansi --verbose --diff --using-cache=yes
PHP CS Fixer 3.13.1 Oliva by Fabien Potencier and Dariusz Ruminski.
PHP runtime: 8.1.13
Loaded config CodeIgniter4 Coding Standards from "/.../codeigniter4login/.php-cs-fixer.dist.php".
FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF.
Legend: .-no changes, F-fixed, S-skipped (cached or empty file), I-invalid file syntax (file ignored), E-error
   1) /.../codeigniter4login/app/Filters/Noauth.php (single_space_after_construct, braces, void_return, declare_strict_types, blank_line_after_opening_tag, single_line_comment_spacing, single_blank_line_before_namespace, ordered_imports)
      ---------- begin diff ----------
--- /.../codeigniter4login/app/Filters/Noauth.php
+++ /.../codeigniter4login/app/Filters/Noauth.php
@@ -1,8 +1,12 @@
-<?php namespace App\Filters;
+<?php

+declare(strict_types=1);
+
+namespace App\Filters;
+
+use CodeIgniter\Filters\FilterInterface;
 use CodeIgniter\HTTP\RequestInterface;
 use CodeIgniter\HTTP\ResponseInterface;
-use CodeIgniter\Filters\FilterInterface;

 class Noauth implements FilterInterface
 {
@@ -9,15 +13,14 @@
     public function before(RequestInterface $request, $arguments = null)
     {
         // Do something here
-        if(session()->get('isLoggedIn')){
-          return redirect()->to('/dashboard');
+        if (session()->get('isLoggedIn')) {
+            return redirect()->to('/dashboard');
         }
-
     }

-    //--------------------------------------------------------------------
+    // --------------------------------------------------------------------

-    public function after(RequestInterface $request, ResponseInterface $response, $arguments = null)
+    public function after(RequestInterface $request, ResponseInterface $response, $arguments = null): void
     {
         // Do something here
     }

      ----------- end diff -----------

...

      ----------- end diff -----------


Fixed 98 of 100 files in 2.825 seconds, 16.000 MB memory used

上記のように修正された差分が表示されました。

問題がなければ、Gitでcommitしてください。

試しに実行した結果を GitHub にアップしておきました。

まとめ

  • CodeIgniter DevKit はCodeIgniterのライブラリとプロジェクトのための開発用のツールキットです。
  • DevKit には php-cs-fixer が含まれており、簡単にCodeIgniter4のコーディングスタイルにコードを修正できます。
  • CodeIgniter4のコーディングスタイルは PSR-12 準拠です。

CodeIgniter DevKit で Rector を使いコードを修正する」 へ続く。

この記事は CodeIgniter Advent Calendar 2022 - Qiita の19日目です。まだ、空きがありますので、興味のある方は気軽に参加してください。

参考

Date: 2022/12/19

Tags: codeigniter, codeigniter4