用 Mockery 模拟 Laravel Model::increment()
Mocking Laravel Model::increment() with Mockery
我在 Laravel 5 事件处理程序中有一行代码,如下所示:
$this->event->batch->increment('attempted_jobs');
$this->event
是调用处理程序的事件,$this->event->batch
包含我的 Batch
模型。所有这些都会增加我数据库中的 attempted_jobs
列,所以它是相当基本的东西。
我希望能够测试这个事件处理程序,我正在使用 Codeception 和 Mockery。我对 $this->event->batch
的模拟看起来像这样:
$batch = m::mock('MyVendor\MyApp\Batch');
$batch->shouldReceive('increment')->once()->with('attempted_jobs');
然而,这会导致问题 - increment()
是 Model
的受保护方法,因此不能被模拟。这是确切的错误:
InvalidArgumentException: increment() cannot be mocked as it a protected method and mocking protected methods is not allowed for this mock
它似乎是使用 __call()
PHP 魔术方法实现的,那么我该如何模拟它呢?我试图创建一个 __call()
模拟,但这会产生大量与未实现的 increment()
方法相关的错误。
问题是因为,如前所述,increment()
是 Illuminate\Database\Eloquent\Model()
的受保护方法。解决这个问题的方法是直接模拟 __call()
方法,像这样:
$batch = m::mock('MyVendor\MyApp\Batch');
$batch->shouldReceive('__call')->with('increment')->once();
(我不确定为什么我第一次尝试时它不起作用)
我在 Laravel 5 事件处理程序中有一行代码,如下所示:
$this->event->batch->increment('attempted_jobs');
$this->event
是调用处理程序的事件,$this->event->batch
包含我的 Batch
模型。所有这些都会增加我数据库中的 attempted_jobs
列,所以它是相当基本的东西。
我希望能够测试这个事件处理程序,我正在使用 Codeception 和 Mockery。我对 $this->event->batch
的模拟看起来像这样:
$batch = m::mock('MyVendor\MyApp\Batch');
$batch->shouldReceive('increment')->once()->with('attempted_jobs');
然而,这会导致问题 - increment()
是 Model
的受保护方法,因此不能被模拟。这是确切的错误:
InvalidArgumentException: increment() cannot be mocked as it a protected method and mocking protected methods is not allowed for this mock
它似乎是使用 __call()
PHP 魔术方法实现的,那么我该如何模拟它呢?我试图创建一个 __call()
模拟,但这会产生大量与未实现的 increment()
方法相关的错误。
问题是因为,如前所述,increment()
是 Illuminate\Database\Eloquent\Model()
的受保护方法。解决这个问题的方法是直接模拟 __call()
方法,像这样:
$batch = m::mock('MyVendor\MyApp\Batch');
$batch->shouldReceive('__call')->with('increment')->once();
(我不确定为什么我第一次尝试时它不起作用)