[php] PHPUnit은 예외가 발생했다고 주장합니까?

assert테스트중인 코드에서 예외가 발생했는지 테스트 할 수있는 것과 같은 것이 있는지 아는 사람이 있습니까?



답변

<?php
require_once 'PHPUnit/Framework.php';

class ExceptionTest extends PHPUnit_Framework_TestCase
{
    public function testException()
    {
        $this->expectException(InvalidArgumentException::class);
        // or for PHPUnit < 5.2
        // $this->setExpectedException(InvalidArgumentException::class);

        //...and then add your test code that generates the exception 
        exampleMethod($anInvalidArgument);
    }
}

expectException () PHPUnit 문서

PHPUnit 작성자 기사 는 예외 모범 사례 테스트에 대한 자세한 설명을 제공합니다.


답변

PHPUnit 9가 출시 될 때까지 docblock 주석을 사용할 수도 있습니다 :

class ExceptionTest extends PHPUnit_Framework_TestCase
{
    /**
     * @expectedException InvalidArgumentException
     */
    public function testException()
    {
        ...
    }
}

PHP 5.5 이상 (특히 네임 스페이스 코드)의 경우 이제는 ::class


답변

당신이 PHP 5.5 이상에서 실행하는 경우 사용할 수있는 ::class해상도를 가지는 클래스의 이름을 얻기 위해 expectException/을setExpectedException . 이것은 몇 가지 이점을 제공합니다.

  • 이름은 네임 스페이스 (있는 경우)로 정규화됩니다.
  • 그것은 string모든 버전의 PHPUnit에서 작동하도록 해결합니다 .
  • IDE에서 코드 완성을 얻습니다.
  • 클래스 이름을 잘못 입력하면 PHP 컴파일러에서 오류가 발생합니다.

예:

namespace \My\Cool\Package;

class AuthTest extends \PHPUnit_Framework_TestCase
{
    public function testLoginFailsForWrongPassword()
    {
        $this->expectException(WrongPasswordException::class);
        Auth::login('Bob', 'wrong');
    }
}

PHP 컴파일

WrongPasswordException::class

으로

"\My\Cool\Package\WrongPasswordException"

PHPUnit이 더 현명하지 않습니다.

참고 : PHPUnit 5.2는를 expectException 대신하여 도입 되었습니다 setExpectedException.


답변

아래 코드는 예외 메시지와 예외 코드를 테스트합니다.

중요 : 예상 예외도 발생하지 않으면 실패합니다.

try{
    $test->methodWhichWillThrowException();//if this method not throw exception it must be fail too.
    $this->fail("Expected exception 1162011 not thrown");
}catch(MySpecificException $e){ //Not catching a generic Exception or the fail function is also catched
    $this->assertEquals(1162011, $e->getCode());
    $this->assertEquals("Exception Message", $e->getMessage());
}


답변

assertException 확장을 사용할 수 있습니다 을 한 번의 테스트 실행 중에 둘 이상의 예외를 선언 .

TestCase에 메소드를 삽입하고 다음을 사용하십시오.

public function testSomething()
{
    $test = function() {
        // some code that has to throw an exception
    };
    $this->assertException( $test, 'InvalidArgumentException', 100, 'expected message' );
}

나는 또한 좋은 코드를 좋아하는 사람들을 위해 특성 을 만들었다 ..


답변

다른 방법은 다음과 같습니다.

$this->expectException(\InvalidArgumentException::class);
$this->expectExceptionMessage('Expected Exception Message');

당신의 테스트 클래스 범위를 확인하십시오 \PHPUnit_Framework_TestCase.


답변

PHPUnit expectException 메소드는 테스트 메소드 당 하나의 예외 만 테스트 할 수 있기 때문에 매우 불편합니다.

이 도우미 함수를 만들어 일부 함수에서 예외가 발생한다고 주장했습니다.

/**
 * Asserts that the given callback throws the given exception.
 *
 * @param string $expectClass The name of the expected exception class
 * @param callable $callback A callback which should throw the exception
 */
protected function assertException(string $expectClass, callable $callback)
{
    try {
        $callback();
    } catch (\Throwable $exception) {
        $this->assertInstanceOf($expectClass, $exception, 'An invalid exception was thrown');
        return;
    }

    $this->fail('No exception was thrown');
}

테스트 클래스에 추가하고 다음과 같이 호출하십시오.

public function testSomething() {
    $this->assertException(\PDOException::class, function() {
        new \PDO('bad:param');
    });
    $this->assertException(\PDOException::class, function() {
        new \PDO('foo:bar');
    });
}