リフレクション + runkit で既存のクラスをスタブ化する PHP ライブラリ

PHP は一度定義したクラスを再定義しようとするとエラーになるので「テスト対象のクラス内で new された別クラスのインスタンスをスタブ化した上で単体テストを書く」みたいなことがなかなかできない。

みんなどうしてるのかよく分からないんだけど、リフレクションと runkit を使ったらできそうなのでライブラリを作ってみた。

以下はシンプルな例で SomeClass#someMethod を上書きして 'override value' を返すように変更している。

<?php
require_once 'PHPStubClass.php';

class SomeClass {
    public function someMethod() {
        return 'this method will be overrided';
    }
}

PHPStubClass::stubClass('SomeClass', array(
    'someMethod' => 'override value'
));

class SomeClassTest extends PHPUnit_Framework_TestCase {
    private $obj;
    public function setup() {
        $this->obj = new SomeClass();
    }
    public function testSomeMethod() {
        $ret = $this->obj->someMethod();
        $this->assertEquals($ret, 'override value');
    }
}

PEAR パッケージにしてあるので、こんな感じでインストールできます。

pear install -f PHPStubClass-0.0.1.tgz

気が向いたら単純に値を返すだけじゃなくて expect とかできる Mock 用のライブラリも作ってみたい。
Mockery が良さそうなので、作るとしたら Mockery に組み込めるようにしたいな。