PHP 5には、完全なreflection APIが付属しており、 クラス、インターフェイス、関数、メソッド、そしてエクステンションについて リバースエンジニアリングを行うことができます。 さらに、このreflection APIは関数、クラス、メソッドに 関するドキュメントコメントも取得することができます。
reflection APIは、Zend Engineのオブジェクト指向エクステンション で、以下のクラスから構成されています。
<?php |
注意: これらのクラスに関する詳細については、次章を参照してください。
以下の例のコードを実行してみましょう。
ReflectionFunctionクラスにより、 関数のリバースエンジニアリングが可能となります。
<?php |
注意: invokeArgs() は PHP 5.1.0 で追加されました。
関数の内部を調べるために、まず、 ReflectionFunctionクラスのインスタンスを 生成する必要があります。 次にこのインスタンスの上のメソッドのどれかをコールすることができます。
例 19-32. ReflectionFunctionクラスの使用法
|
注意: invoke()メソッドは、 call_user_func()と同様に 可変長の引数をとります。
ReflectionParameterクラスは、 関数またはメソッドのパラメータに関する情報を取得します。
<?php |
注意: isOptional(), isDefaultValueAvailable(), isOptional() は、PHP 5.1.0で追加されました。
関数パラメータの内部を調べる際には、まず、 ReflectionFunction クラスまたは ReflectionMethod クラスのインスタンスを 作成する必要があります。 次に、配列のパラメータを取得するために、そのインスタンスの getParameters()メソッドを使用してください。
例 19-33. ReflectionParameterクラスの使用
|
ReflectionClassクラスにより、 クラスのリバースエンジニアリングが可能となります。
<?php |
注意: hasConstant(), hasMethod(), hasProperty() は、PHP 5.1.0 で追加されました。
クラスのイントロスペクションを行うには、まず ReflectionClass クラスのインスタンスを生成する必要があります。それから、 このインスタンスのメソッドをコールしてください。
例 19-34. ReflectionClassクラスの使用法
|
注意: newInstance()メソッドは、 call_user_func()と同様に 可変長の引数をとります。
注意: $class = new ReflectionClass('Foo'); $class->isInstance($arg) は、$arg instanceof Foo または is_a($arg, 'Foo')と等価です。
ReflectionMethodクラスにより、 クラスメソッドのリバースエンジニアリングが可能となります。
<?php |
メソッドの内部を調べるために、まず、 ReflectionMethodクラスのインスタンスを 生成する必要があります。 次にこのインスタンスの上のメソッドのどれかをコールすることができます。
例 19-35. ReflectionMethodクラスの使用
|
注意: private, protectedまたはabstractメソッドのinvokeを行うと、 invoke()から例外がスローされます。
注意: 上記のstaticメソッドの場合、 invoke()の最初の引数にNULLを渡す必要があります。 staticでないメソッドの場合、ここにクラスのインスタンスを指定してください。
ReflectionPropertyクラスにより、 クラスプロパティに関する リバースエンジニアリングが可能となります。
<?php |
プロパティの内部を調べるために、まず、 ReflectionPropertyクラスのインスタンスを 生成する必要があります。 次にこのインスタンスの上のメソッドのどれかをコールすることができます。
例 19-36. ReflectionPropertyクラスの使用
|
注意: privateまたはprotectedクラスプロパティの値の取得または設定を 行うと、例外がスローされます。
The ReflectionExtensionクラスにより、 エクステンションのリバースエンジニアリングが可能となります。 実行時にロードされている全てのエクステンションを get_loaded_extensions()により取得することができます。
<?php |
メソッドの内部を調べるために、まず、 ReflectionExtensionクラスのインスタンスを 生成する必要があります。 次にこのインスタンスの上のメソッドのどれかをコールすることができます。
例 19-37. ReflectionExtensionクラスの使用
|
組み込みクラスの特別なバージョンを作成したい場合 (例えば、、エクスポートする際に、色づけしたHTMLを作成したり、 メソッドの代わりに簡単にアクセスできるメンバー変数を作成したり、 補助的なメソッドを作成したり、)、 Reflectionクラスを拡張することができます。
例 19-38. 組み込みクラスを拡張する
|
注意: 注意: Iコンストラクタを上書きした場合、 挿入するコードの前に 親クラスのコンストラクタをコールしわすれないようにしてください。 これを怠ると、以下のようなエラーを発生します。 Fatal error: Internal error: Failed to retrieve the reflection object