【问题标题】:Laravel PhpUnit Dependency InjectionLaravel PhpUnit 依赖注入
【发布时间】:2022-01-16 03:40:20
【问题描述】:

我正在使用依赖注入来调用 Laravel 中的自定义服务,它工作正常。但是当我使用接口将这些依赖项注入我的 Phpunit 测试用例类时,我收到以下错误:

目标 [App\Services\Interfaces\CarServiceInterface] 不可实例化。

虽然接口已正确绑定到提供程序中的目标具体类。
我使用了不同的样式,例如通过__construct() 方法注入、注入到测试方法甚至调用app() 方法,但它们都不起作用。

测试文件:

private $carService;

public function setUp(): void
{
    parent::setUp();

    $this->carService = app(CarServiceInterface::class);
}

提供者:

$this->app->bind(
    App\Services\Interfaces\CarServiceInterface::class,
    App\Services\CarService::class
);

这样做的正确方法是什么?

【问题讨论】:

  • 你在哪里写你的测试?在单元测试还是在功能测试部分?
  • @BABAKASHRAFI 在单元测试中
  • 您需要在功能测试部分编写您的测试,因为它继承自具有CreatesApplication 特征的自定义测试用例。
  • @BABAKASHRAFI 好吧,我将测试移至功能部分,但我仍然收到错误。
  • 可能是绑定错误。

标签: laravel unit-testing dependency-injection phpunit


【解决方案1】:

您需要在特性部分编写测试,因为特性测试是从 laravel 基本测试用例继承的,并且它们具有 CreatesApplication 特征。 Refer to here

之后,您可以在测试中使用app('Your abstract class namespace ') 方法或$this->app->make('Your abstract class namespace ') 简单地获取具体的类实例。

【讨论】:

    【解决方案2】:

    显然是错误的测试方法。 为什么在测试课上需要 DI?! 在测试类中,您必须准备并可能绑定/模拟所需的类。 然后测试你的代码。

    错误的第二部分表明,尽管您的假设,该类没有正确绑定。

    顺便说一句,如果你认为我错过了什么,而你需要 DI,请使用 bindsingleton 方法。

    $this->app->bind(CarServiceInterface::class, fn () => $exampleInstance);
    
    //or 
    
    $this->app->singleton(CarServiceInterface::class, fn () => $exampleInstance);
    

    现在您可以像这样使用容器访问您的界面而不会出现 DI 错误:

    $this->app[CarServiceInterface::class]
    //or
    $this->app->make(CarServiceInterface::class)
    //or
    app(CarServiceInterface::class)
    

    【讨论】:

      【解决方案3】:

      好吧,我终于找到了问题所在。尽管其他人给出的所有答案/建议也是正确的。
      我的测试用例类扩展了错误的 TestCase 命名空间。通过将其更改为App\TestCase,它得到了修复。

      【讨论】:

        猜你喜欢
        • 2016-07-19
        • 2023-03-23
        • 2014-02-02
        • 1970-01-01
        • 2018-02-20
        • 2015-03-02
        • 2017-09-27
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多