我重构了一些控制器,以便通过属性注入as recommended in the "best practices"使用依赖注入
final class ZebraController extends Controller
{
/**
* @Inject
* @var AnimalClientInterface
*/
private $animalsRestClient;
public function fetchAllZebras(ServerRequestInterface $req): ResponseInterface {
// ...
}
}我的PHP-DI配置被配置为为AnimalClientInterface注入AnimalClient对象的一个实例,这在实现代码中很好用,因为只有一个真正的AnimalClient。
在我的单元测试中,我需要向这个属性注入一个MockZebraClient。我不能像对AnimalClient所做的那样简单地配置它,因为其他类可能有类似的注释,但例如需要一个MockTigerClient来进行测试。
这是我的单元测试:
class ZebraControllerTest extends TestCase
{
/** @var ZebraController */
protected $object;
public function testFetchAllZebras(): void {
// assertions here
}
}我认为使用injectOn method是解决这个问题的正确方法,但是我不知道如何配置容器来为正确的测试选择正确的模拟对象。
由于遗留的代码结构,构造函数注入是不可能的。应用程序中的所有控制器都需要重构以使用DI,以便更改Controller的构造函数。
发布于 2019-01-23 00:09:53
也许有一个特定于PHP-DI的答案,但我不熟悉它。在你的例子中,定义构造函数似乎也是不被允许的。鉴于此,您可以使用静态伪装构造函数进行测试,它允许访问设置内部状态:
<?php
class A {
private $b;
public static function construct($b) {
$a = new A();
$a->b = $b;
return $a;
}
}
class B {
}
$a = A::construct(new B());
var_dump($a);返回:
object(A)#2 (1) { "b":"A":private=> object(B)#1 (0) {} }
https://stackoverflow.com/questions/54284024
复制相似问题