如何正确地模拟来自Laravel的Illuminate \ Http \ Request类

时间:2017-12-12 16:25:01

标签: php laravel unit-testing mocking mockery

我正在尝试从一个类中测试一个方法,该类包含一个使用Laravel的request()帮助器的方法。这是方法:

类别

public function getCanonicalUrl()
{
    return preg_match('/\/sale\/./', request()->getRequestUri())
         ? ''
         : url($this->getUrlKey());
}

测试应该让这个助手在执行 getRequestUri()时正确捕获URI,但实际上它返回一个空字符串。这是我给测试的一千次尝试之一。

测试

public function testCanonical()
{
    // ...

    $requestMock = Mockery::mock(Request::class)
      ->shouldReceive('getRequestUri')
      ->andReturn('/sale/random-string');

    $this->app->instance(Request::class, $requestMock);

    // ...
}

有关如何实现这一目标的任何想法? 提前谢谢。

2 个答案:

答案 0 :(得分:3)

  

你不应该嘲笑Request门面。相反,将您想要的输入传递给HTTP帮助程序方法,例如运行测试时的get和post。

https://laravel.com/docs/5.5/mocking#mocking-facades

答案 1 :(得分:0)

https://stackoverflow.com/a/61903688/135114, 如果

  1. 您正在测试的函数带有一个$request参数,并且
  2. 您不需要对Request做一些时髦的事情-实际的路线路径对您来说已经足够

...那么您无需“嘲笑”一个请求(例如嘲笑),
您可以创建一个Request 并通过它,例如

public function test_myFunc_condition_expectedResult() {
    ...
    $mockRequest = Request::create('/path/that/I_want', 'GET'); 
    $this->assertTrue($myClass->myFuncThat($mockRequest));
}