11

のPHPUnit ドキュメントによると@expectedExceptionMessage、文字列は実際Exceptionにスローされた文字列の部分文字列のみである必要があります。

私の検証方法の 1 つでは、エラーが発生するたびに配列項目がプッシュExceptionされ、エラーの配列を内破することによって最終的なメッセージが表示されます。

class MyClass
{
    public function validate($a, $b, $c, $d)
    {
        if($a < $b) $errors[] = "a < b.";
        if($b < $c) $errors[] = "b < c.";
        if($c < $d) $errors[] = "c < d.";

        if(count($errors) > 0) throw new \Exception(trim(implode(" ", $errors)));
    }
}

ここでの問題は、PHPUnit テスト メソッドでさまざまな組み合わせをチェックすることです。これにより、失敗するつもりのテストが成功します。

/**
 * @expectedException \Exception
 * @expectedExceptionMessage a < b.
 */
public function testValues_ALessBOnly()
{
    $myClass = new MyClass()
    $myClass->validate(1, 2, 4, 3);
}

メッセージの文字列Exceptionは実際にはありますが"a < b. b < c."、このテストは引き続きパスします。メッセージが期待どおりではないため、このテストは失敗するつもりです。

PHPUnitで部分文字列ではなく正確な文字列を期待する方法はありますか? 次のことは避けたいと思います。

public function testValues_ALessBOnly()
{
    $myClass = new MyClass()
    $fail = FALSE;

    try
    {
        $myClass->validate(1, 2, 4, 3);
    }
    catch(\Exception $e)
    {
        $fail = TRUE;
        $this->assertEquals($e->getMessage(), "a < b.";
    }

    if(!$fail) $this->fail("No Exceptions were thrown.");
}
4

6 に答える 6

2

例外をテストするためにさまざまな方法を試しましたが、最終的に、例外をテストする最良の方法は try-catch ブロックであることがわかりました。例外コードで例外をスローし、このコードで例外がスローされるかどうかをテストすることをお勧めします。たとえば、例外コードが 101 であるとします。

if(count($errors) > 0) throw new \Exception(trim(implode(" ", $errors)), 101);

たとえば、例外コードが 101 であるとします。

try {
    $myClass->validate(1, 2, 4, 3);
    $this->fail( "Exception with 101 code should be thrown" );
} catch (Exception $e) {
    $this->assertEquals( 101, $e->getCode());
}
于 2013-09-06T10:38:51.433 に答える
0

エラーが発生したことを確認するための別の解決策:

        $errorHappened = false;
        try {
            //call your code here 
        } catch (\Exception $e) {
            $errorHappened = true;
            $this->assertEquals($e->getMessage(), "Expected error text");
            $this->assertEquals($e->getCode(), "Expected error code");
        }
        $this->assertTrue($errorHappened);
于 2019-10-09T14:50:17.950 に答える