Laravel phpunit 模拟模型第一个函数

Posted

技术标签:

【中文标题】Laravel phpunit 模拟模型第一个函数【英文标题】:Laravel phpunit mock model first function 【发布时间】:2021-06-27 13:39:29 【问题描述】:

我正在尝试模拟我在数据库上进行查询的模型。起初我在下面嘲笑where 函数,但后来我意识到它实际上是first 提供了结果,但这仍然不起作用。我知道我可以只使用数据库,但是我们的 docker 设置非常慢,而且我不能使用 SQLite,因为以前的开发人员在某个时候创建​​了一个迁移,删除了外键。

测试:

protected function setUp(): void

    parent::setUp();

    $this->calendarEventBookingRepository = app(CalendarEventBookingRepository::class);

    $this->calendarEventBooking = Mockery::mock(CalendarEventBooking::class);


/** @test */
function bookSingleCustomerReturnsNull()

    $calendarEvent = factory(CalendarEvent::class)->create();
    $calendarEventBooking = factory(CalendarEventBooking::class);

    $data = new \stdClass();
    $data->customer_id = 1;

    $this->calendarEventBooking->shouldReceive('first')->once()->andReturn($calendarEventBooking);
    $this->app->instance(CalendarEventBooking::class, $this->calendarEventBooking);

    $result = $this->calendarEventBookingRepository->bookSingleCustomer($calendarEvent, $data);

    $this->assertEquals(null, $result);

正在测试的功能:

public function bookSingleCustomer(CalendarEvent  $event, $data)

    $this->event = $event;

    DB::transaction(function () use ($data) 
        $alreadyBooked = $this->modelClassName::where([
            ['customer_id', $data->customer_id]
        ])->first();

        if ($alreadyBooked) 
            return null;
        

        return "hello";
    );

测试输出:

Mockery\Exception\InvalidCountException: Method first(<Any Arguments>) from Mockery_0_Models_CalendarEventBooking should be called
 exactly 1 times but called 0 times.

【问题讨论】:

这是由于 Laravel orm 如何绑定到模型,在我看来,模拟 laravel 模型是浪费时间,没有人在更高的规模上这样做 afaik。通常有两种方法可以解决这个问题,使用 sqlite 作为您的测试数据库,并且永远不要点击我更喜欢的“正确”数据库。另一种方法是将您的模型逻辑封装在服务或类似物中,然后模拟服务而不是 laravel 模型。如果您想走这些路线,我可以帮助您实现这两个目标:) 从另一篇帖子中公然复制粘贴。 【参考方案1】:

我认为你也应该模拟 where 方法。

$this->calendarEventBooking->method('where')->willReturnSelf();

【讨论】:

以上是关于Laravel phpunit 模拟模型第一个函数的主要内容,如果未能解决你的问题,请参考以下文章

PhpUnit - 用关系模拟 laravel 模型

在 PHPUnit 中调用路由时如何在 Laravel 8 中模拟 Eloquent 模型

用于 PHPunit 的 Laravel 5.4 模型模拟

使用 Laravel 和 PHPUnit 模拟函数

PHPUnit 问题断言模拟是使用 Laravel 的 ReflectionProperty 对象

在 Laravel 中使用 Mockery/phpUnit 时出错