2

XmlRPC-Api の低レベルの実装を作成しましたが、通信をテストするのに苦労しました。

これが私のコードです。

abstract class BaseClient
{
    protected function call($method, array $params = array())
    {
        $request = xmlrpc_encode_request($method, $parameters);

        $file = file_get_contents($this->getDSN(), false, $context);
        $response = xmlrpc_decode($file);

        if ($response && xmlrpc_is_fault(array($response))) {
            trigger_error("xmlrpc: {$response[faultString]} ({$response[faultCode]})");
        }

        return $response;
    }
}


Client extends BaseClient
{
    public function testCall($msg)
    {
        return $this->call('testMethid', array($msg));
    }
}

そして、これが私のテストです。

ClientTest extends PHPUnit_FrameWork_TestCase
{
    public function testTestCall()
    {
        $c = new Client();
        $resp = $c->testCall('Hello World');

        $this->assertEquals('Hello World', $resp);
    }
}

テスト環境内で API にアクセスできないため、このテストは毎回クラッシュします。関数をモックして注入する解決策がわかりませんcall。私に何ができる?私のオブジェクト構造が悪くてテストできないのかもしれませんが、どうすればこの構造を改善できますか (これが起こった場合)?

乾杯。

4

2 に答える 2

2

外部 API をテストしようとしているので、file_get_contents()呼び出しを別のクラスでラップし、それを BaseClient に注入することから始めます。最も単純な形式では、次のようになります。

class RemoteFileRetriever
{
    public function retrieveFileContents($url)
    {
        // Do some work to create $context
        ...

        // Now grab the file contents
        $contents = file_get_contents($url, false, $context);

        return $contents;
    }
}

abstract class BaseClient
{
    private $fileRetriever;

    public function __construct(RemoteFileRetriever $fileRetriever)
    {
        $this->fileRetriever = $fileRetriever;
    }

    protected function call($method, array $params = array())
    {
        ...

        $file = $this->fileRetriever->retrieveFileContents($this->getDSN());

        ...
    }
}

テストでは、モック オブジェクトを使用して、ファイル リトリーバーとして挿入できます。例えば:

class ClientTest extends PHPUnit_FrameWork_TestCase
{
    public function testTestCall()
    {
        $mockRetriever = new MockRemoteFileRetriever();
        $c = new Client($mockRetriever);
        $resp = $c->testCall('Hello World');

        $this->assertEquals('Hello World', $resp);
    }
}

PHPUnit には、実際にモック用のヘルパーが組み込まれています。PHPUnit のモック オブジェクトを参照してください。

于 2013-08-15T14:22:17.940 に答える
0

関数をモックしたくありませんcall

偽のサービスをセットアップできない場合は、PHP Namespacing (PHP 5.3 が必要) を使用して実行できる php 関数をモックする必要があります。その後、call メソッドで呼び出している内部 PHP 関数のモックを作成できます。

http://www.schmengler-se.de/-php-mocking-built-in-functions-like-time-in-unit-tests

これができない場合、テストはかなり困難になる可能性があります。テスト用にヒットできる偽の API を作成できますか? API のメソッドを実際にテストしているわけではなく、コードが API へのリクエストを作成し、意図した方法でレスポンスを処理していることを確認しようとしていることに注意してください。

原則として、サードパーティのコードはテスト済みで、適切に動作すると想定してください。

于 2013-08-15T14:15:30.383 に答える