如何使用构造函数测试symfony表单类型


How to test a symfony form type with constructor

我目前正在与Symfony的TypeTestCase使用构造函数测试表单类型作斗争。虽然正式解决方案将表单注册为服务在应用程序中运行良好,但无法使用 TypeTestCase 测试相同的表单类型。由于TypeTestCase从FormIntegrationTestCase扩展而来,并且从''PHPUnit_Framework_TestCase而不是KernelTestCase扩展。TypeTestCase 中的 FormFactory 不会/不能查找注册为服务的表单,并引发调用 phpunit 的错误:

Tests'DemoBundle'Form'Type'DemoTypeTest::testSubmitValidData
Missing argument 1 for DemoBundle'Form'Type'DemoType::__construct(), called in /var/www/vendor/symfony/symfony/src/Symfony/Component/Form/FormRegistry.php on line 90 and defined

我目前看到的唯一方法是不使用配置选项中的选项解析器通过构造函数提供依赖项,并使用依赖项的 setRequired 方法设置必需元素。

这里从代码中获取相关部分:

演示类型.php

[...]
class DemoType extends AbstractType
{
    /**
     * @var EntityManager
     */
    protected $entityManager;
    public function __construct($entityManager)
    {
        $this->entityManager = $entityManager;
    }
[...]

服务.yml

app.form.type.demo:
    class: DemoBundle'Form'Type'DemoType
    arguments: ["@doctrine.orm.entity_manager"]
    tags:
        - { name: form.type }

演示类型测试.php

[...]
class DemoTypeTest extends TypeTestCase
{
    protected function getExtensions()
    {
        $classMetadata = $this->getMock(ClassMetadata::class, [], [], '', false);
        /* @var ValidatorInterface|'PHPUnit_Framework_MockObject_MockObject $validator */
        $validator = $this->getMock(ValidatorInterface::class);
        $validator->method('validate')->will($this->returnValue(new ConstraintViolationList()));
        $validator->method('getMetadataFor')->will($this->returnValue($classMetadata));
        return [
            new ValidatorExtension($validator),
        ];
    }
    public function testSubmitValidData()
    {
        $formData = [
            'some' => 'data',
        ];
        $form = $this->factory->create(DemoType::class);
[...]

您可以实例化 FormType 并将其传递给表单工厂,如文档中所述。

您可以模拟原则实体管理器,例如:

public function testSubmitValidData()
{
  // Mock the FormType: entity
  $em = $this->getMockBuilder(''Doctrine'ORM'EntityManager')
      ->disableOriginalConstructor()
      ->getMock();
    $type = new DemoType($em);
    $formData = [
        'some' => 'data',
    ];
    $form = $this->factory->create($type);
    ...

关于模拟 Doctrine 对象堆栈以模拟 repo 方法的示例,您可以查看此答案或简单地询问:)

希望这个帮助