Php 单元测试中处理Laravel HttpException

Php 单元测试中处理Laravel HttpException,php,unit-testing,symfony,laravel,laravel-4,Php,Unit Testing,Symfony,Laravel,Laravel 4,我在Laravel中的一个单元测试函数一直在出错。我试图断言,在不满足特定条件的情况下请求特定页面会触发403禁止的错误 我的测试用例功能如下: public function testNoAjaxCall() { $this->call('POST', 'xyz', array()); $this->assertResponseStatus(403); } 在控制器操作中,这是路由到的,我有: if(!Input::has('ajax') || Input:

我在Laravel中的一个单元测试函数一直在出错。我试图断言,在不满足特定条件的情况下请求特定页面会触发403禁止的错误

我的测试用例功能如下:

public function testNoAjaxCall() {

    $this->call('POST', 'xyz', array());

    $this->assertResponseStatus(403);

}
在控制器操作中,这是路由到的,我有:

if(!Input::has('ajax') || Input::get('ajax') != 1) {

    // Drop all 'non-ajax' requests.
    App::abort(403, 'Normal POST requests to this page are forbidden. Please explicitly tell me you\'re using AJAX by passing ajax = 1.');

}
运行phpunit返回以下内容:

1) RaceTest::testNoAjaxCall

Symfony\Component\HttpKernel\Exception\HttpException:禁止对此页面的正常POST请求。请通过传递AJAX=1明确地告诉我您正在使用AJAX

[path\to\laravel]\vendor\laravel\framework\src\illumb\Foundation\Application.php:875

[修订的堆栈跟踪]

[path\to\laravel]\vendor\symfony\http kernel\symfony\Component\HttpKernel\Client.php:81

[path\to\laravel]\vendor\symfony\browser kit\symfony\Component\browser kit\Client.php:325

[path\to\laravel]\vendor\laravel\framework\src\illumb\Foundation\Testing\TestCase.php:74

[path\to\laravel]\app\tests[testFileName].php:176

失败

测试:6次,断言:17次,错误:1次

当然,堆栈跟踪指向
$this->call(..)
应用程序::中止(..)

我在
app/start/global.php
文件中有一个HttpException错误处理程序,当在单元测试之外触发它时(例如,直接向被测试的URL发出
POST
请求),该处理程序会起作用,但单元测试似乎无法正确捕获异常,甚至无法到达断言调用

我遗漏了什么?

应该已经解释清楚了

/**
 * @expectedException \Symfony\Component\HttpKernel\Exception\HttpException
 * @expectedExceptionMessage Normal POST requests to this page are forbidden. Please explicitly tell me you\'re using AJAX by passing ajax = 1.
 */
public function testNoAjaxCall() {

    $this->call('POST', 'xyz', array());

}

到目前为止,我发现的断言HttpException状态代码的最佳方法可以在Sirbillance的工作中找到

TestCase.php:

public function assertHTTPExceptionStatus($expectedStatusCode, Closure $codeThatShouldThrow)
{
    try 
    {
        $codeThatShouldThrow($this);

        $this->assertFalse(true, "An HttpException should have been thrown by the provided Closure.");
    } 
    catch (\Symfony\Component\HttpKernel\Exception\HttpException $e) 
    {
        // assertResponseStatus() won't work because the response object is null
        $this->assertEquals(
            $expectedStatusCode,
            $e->getStatusCode(),
            sprintf("Expected an HTTP status of %d but got %d.", $expectedStatusCode, $e->getStatusCode())
        );
    }
}
用法:

public function testGetFailsWith403()
{
    $this->assertHTTPExceptionStatus(403, function ($_this)
    {
        $_this->call('GET', '/thing-that-should-fail');
    });
}

多亏了PHP单元的内置解析器,这一点是可以实现的。这很奇怪,因为Laravel提供了自己的断言助手方法,如果无法访问这些方法,这些方法似乎是无用的。()