結論
PHP の ReflectionClass を使えば可能です。
<?php // 例えば、 CarbonInterface の定義されているファイルが見たい場合 $a = new \ReflectionClass(CarbonInterface::class); var_dump($a->getFileName());
どういう時に使うの?
PHP には autoload という機能があり、皆さん普通はこの autoload を利用しているかと思います。
しかし、
- 同じライブラリの複数バージョンがインストールされている
- 全く同じクラスが複数定義されている
といった場合に、想定と異なるクラスが autoload され、不具合の原因になることがあります。
この時に、「実際にはどのクラスがロードされているのか?」を調べるために、この ReflectionClass::getFileName を利用します。
Carbon と Chronos の例
PHP における DateTime のライブラリとして、 Carbon と Chronos があります。
Chronos は、 CakePHP で開発されたライブラリです。CakePHPはもともと Carbon を採用していましたが、途中から Chronos という独自のライブラリを使うようになりました。
Chronos 1.2.2 以前のバージョンでは、 Carbon との互換性を保つために、以下のコードが入っています。
https://github.com/cakephp/chronos/blob/1.2.2/src/carbon_compat.php
Carbon と Chronos が両方インストールされている環境で、 CarbonInterface を利用しようとすると、上記コードの影響で、 ChronosInterface
が読み込まれることになります。
<?php $a = new \ReflectionClass(CarbonInterface::class); var_dump($a->getFileName());
結果
..../vendor/cakephp/chronos/src/ChronosInterface.php
Chronos と Laravel
私の場合、Chronos がインストールされた環境に Laravel をインストールしたところ、Laravel が起動せず、 var_dump や ReflectionClass::getFileName を使って地道に調査したところ、 Laravel で使われている Carbon と、すでにインストールされている古いバージョンの Chronos が競合を起こしており、Laravel が起動しないことに気づきました。
PHP では、実際にどのファイルが autoload されているのか、すぐにはわからないため、このテクは有用です。