【问题标题】:Environment specific data fixtures with Symfony+Doctrine使用 Symfony+Doctrine 的环境特定数据夹具
【发布时间】:2012-08-02 19:34:20
【问题描述】:

使用 Smyfony2 和 Doctrin2,可以使用以下示例创建数据夹具:http://symfony.com/doc/current/bundles/DoctrineFixturesBundle/index.html

我希望能够使用这个概念进行测试,以便 setup/teardown 可以为功能测试创建一个纯测试数据环境。如何在功能测试期间运行一组特定的仅用于测试的固定装置,以及如何将这些固定装置与标准固定装置分开,以便控制台命令忽略它们?

似乎这样做的方法是复制教义:fixtures 控制台命令的功能并将测试夹具存储在其他地方。谁有更好的解决方案?

【问题讨论】:

    标签: symfony doctrine-orm


    【解决方案1】:

    按目录拆分fixture 的另一种方法是使用自定义fixture 类。然后,您的夹具类将扩展此类并指定实际加载它的环境。

    <?php
    
    use Doctrine\Common\DataFixtures\FixtureInterface;
    use Doctrine\Common\Persistence\ObjectManager;
    use Symfony\Component\DependencyInjection\ContainerAwareInterface;
    use Symfony\Component\DependencyInjection\ContainerInterface;
    use Symfony\Component\HttpKernel\KernelInterface;
    
    /**
     * Provides support for environment specific fixtures.
     *
     * This container aware, abstract data fixture is used to only allow loading in
     * specific environments. The environments the data fixture will be loaded in is
     * determined by the list of environment names returned by `getEnvironments()`.
     *
     * > The fixture will still be shown as having been loaded by the Doctrine
     * > command, `doctrine:fixtures:load`, despite not having been actually
     * > loaded.
     *
     * @author Kevin Herrera <kevin@herrera.io>
     */
    abstract class AbstractDataFixture implements ContainerAwareInterface, FixtureInterface
    {
        /**
         * The dependency injection container.
         *
         * @var ContainerInterface
         */
        protected $container;
    
        /**
         * {@inheritDoc}
         */
        public function load(ObjectManager $manager)
        {
            /** @var KernelInterface $kernel */
            $kernel = $this->container->get('kernel');
    
            if (in_array($kernel->getEnvironment(), $this->getEnvironments())) {
                $this->doLoad($manager);
            }
        }
    
        /**
         * {@inheritDoc}
         */
        public function setContainer(ContainerInterface $container = null)
        {
            $this->container = $container;
        }
    
        /**
         * Performs the actual fixtures loading.
         *
         * @see \Doctrine\Common\DataFixtures\FixtureInterface::load()
         *
         * @param ObjectManager $manager The object manager.
         */
        abstract protected function doLoad(ObjectManager $manager);
    
        /**
         * Returns the environments the fixtures may be loaded in.
         *
         * @return array The name of the environments.
         */
        abstract protected function getEnvironments();
    }
    

    你的灯具最终会是这样的:

    <?php
    
    namespace Vendor\Bundle\ExampleBundle\DataFixtures\ORM;
    
    use AbstractDataFixture;
    use Doctrine\Common\Persistence\ObjectManager;
    
    /**
     * Loads data only on "prod".
     */
    class ExampleData extends AbstractDataFixture
    {
        /**
         * @override
         */
        protected function doLoad(ObjectManager $manager)
        {
            // ... snip ...
        }
    
        /**
         * @override
         */
        protected function getEnvironments()
        {
            return array('prod');
        }
    }
    

    我相信这应该适用于 ORM 和 ODM 数据夹具。

    【讨论】:

    • 如何从控制台定义环境?使用php app/console fixture:load --env=prod ?
    • 回答我自己:是的,php app/console fixture:load --env=prod 与提供的解决方案一起使用 :)
    • 哇。太棒了!
    【解决方案2】:

    最简单的方法是将您的灯具放入不同的文件夹,然后使用php app/console doctrine:fixtures:load --fixtures=../src/Acme/TestBundle/DataFixtures/ORM/test 命令加载它们。 fixtures 选项必须指向你的应用文件夹的相对路径!

    然后,您可以根据需要将数据拆分为初始数据、测试数据等,或者创建开发、测试、暂存、产品固定装置。

    如果您想将它们混合在一起,我不知道有什么比我做的更好的解决方案:我创建了一个“模板”文件夹,所有灯具都驻留在其中。在我的 dev 文件夹中,我创建了一个扩展正确的类模板中的夹具类并调整需要调整的内容(如覆盖getOrder 方法)。它并不完美,我想有人可以考虑扩展 fixtures:load 命令以采用多条路径,但它对我有用。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2010-12-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-10-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多