Jam*_*May 5 php phpunit symfony php-7.2
我正在尝试将我在 Symfony 3.3 和 php 7.1 上运行的应用程序升级到 php 7.2,但是当我运行 phpunit 时遇到了大量已弃用的消息。最烦人的是:
"user.user_service" 服务已经初始化,替换它自 Symfony 3.3 起已被弃用,并将在 4.0: 7x 中失败
这是因为我在 setUp 方法中有这一行:
$this->userService = $this->getMockBuilder(UserService::class)
->setMethods(['update'])
->getMock();
$container->set('user.user_service', $this->userService);
Run Code Online (Sandbox Code Playgroud)
7x 是因为我在那个班级有 7 个测试用例,并且为每个测试用例触发了 setUp。我该如何处理这个问题?我无法删除这个模拟,因为它很重要。
我不明白为什么 Symfony 完全指向这个测试用例,因为我在所有测试中都以这种方式替换了很多服务。在这个setUp方法之前我没有在任何地方替换这个服务,所以很奇怪。
因此,构建容器后,容器是不可变的,您不能向其中添加其他服务/参数(也可以替换,因为这包含两个操作 - 删除和设置)。
但是,在更多情况下,我们应该有机会替换服务内的逻辑。
为此,我仅使用自定义服务进行测试。此服务覆盖默认服务 ( class TestUserService extends UserService) 或使用接口(更好)。创建类后,我在另一个机会中或通过另一个机会声明具有相同名称的服务app/config/test.yml (when@test)。
namespace Acme;
interface UserServiceInterface
{
public function create(object $some): User;
}
/* Original service */
readonly class UserService implements UserServiceInterface
{
public function create(object $some): User
{
// Some actions here
}
}
/* Service only for test */
class TestUserService implements UserServiceInterface
{
private ?\Closure $callback;
public function shouldExecute(\Closure $callback): void
{
$this->callback = $callback;
}
public function create(object $some): User
{
if ($this->callback) {
return ($this->callback)($some);
}
throw new \RuntimeException(\sprintf(
'The service %s wrong configured. Please call "shouldExecute" method previously.',
__CLASS__
));
}
}
Run Code Online (Sandbox Code Playgroud)
并在您的配置中声明它(以 YAML 为例):
services:
user_service:
class: Acme\UserService
when@test:
services:
user_service:
class: Acme\TestUserService
Run Code Online (Sandbox Code Playgroud)
之后,我可以轻松地将内部的任何逻辑UserService::create仅用于测试环境。
class SomeTest extends TestCase
{
private TestUserService $userService;
protected function setUp(): void
{
$this->userService = self::getContainer()->get('user_service');
}
public function shouldSuccess(): void
{
$this->userService->shouldExecute(static function (object $some) {
self::assertEquals('foo bar', $some);
return new User();
});
// logic for testing
}
}
Run Code Online (Sandbox Code Playgroud)
在少数情况下,开发人员希望有机会仅在特定情况下更改逻辑。为此,我们可以使用装饰器模式,如果未配置回调,则UserService在内部调用 origin 。TestUserService
| 归档时间: |
|
| 查看次数: |
2563 次 |
| 最近记录: |