【问题标题】:Children count depends on method in test儿童计数取决于测试方法
【发布时间】:2015-04-06 22:54:51
【问题描述】:

在尝试使用自引用 ManyToOne 实体时,我发现子项的数量取决于用于查找父项的方法。如果使用存储库,则测试失败并显示Failed asserting that 1 matches expected 2。如果改为使用 DQL,则测试成功。请参阅下面的测试部分中的testTwoKids()。我已经在调试中确认数据库中的实际计数在这两种情况下都是 2。

我的猜测是实体定义有问题。

实体:

class Category
{
    /**
     * @var integer
     *
     * @ORM\Column(name="id", type="integer", nullable=false)
     * @ORM\Id
     * @ORM\GeneratedValue(strategy="IDENTITY")
     */
    protected $id;

    /**
     * @ORM\Column(name="name", type="string", nullable=false)
     */
    private $name;

    /**
     * @ORM\OneToMany(targetEntity="Category", mappedBy="parent")
     **/
    private $children;

    /**
     * @ORM\ManyToOne(targetEntity="Category", inversedBy="children", cascade={"persist","remove"})
    *  @ORM\JoinColumn(name="parent_id", referencedColumnName="id")
     **/
    private $parent;

    public function __construct() {
        $this->children = new ArrayCollection();
    }

    public function addChildren($child)
    {
        $this->children[] = $child;

        return $this;
    }

    public function setName($name)
    {
        $this->name = $name;
    }

    public function getName()
    {
        return $this->name;
    }

    public function setParent($parent)
    {
        $this->parent = $parent;
    }

    public function getParent()
    {
        return $this->parent;
    }

    /**
     * Get id
     *
     * @return integer 
     */
    public function getId()
    {
        return $this->id;
    }

    /**
     * Add children
     *
     * @param \AppBundle\Entity\Category $children
     * @return Category
     */
    public function addChild($child)
    {
        $this->children->add($child);
        $child->setParent($this);

        return $this;
    }

    /**
     * Remove children
     *
     * @param \AppBundle\Entity\Category $children
     */
    public function removeChild(\AppBundle\Entity\Category $children)
    {
        $this->children->removeElement($children);
    }

    /**
     * Get children
     *
     * @return \Doctrine\Common\Collections\Collection 
     */
    public function getChildren()
    {
        return $this->children;
    }
}

测试

class CategoryTest extends KernelTestCase
{

    /**
     * @var \Doctrine\ORM\EntityManager
     */
    private $em;

    /**
     * {@inheritDoc}
     */
    public function setUp()
    {
        self::bootKernel();
        $this->em = static::$kernel->getContainer()
                ->get('doctrine')
                ->getManager()
        ;
        $product = new \AppBundle\Entity\Product();
        $product->setName('foo');
        $this->em->persist($product);

        $cat = new \AppBundle\Entity\Category();
        $cat->setName('Hook');

        $child = new \AppBundle\Entity\Category();
        $child->setName('Dry');
        $child->setParent($cat);
        $this->em->persist($child);

        $this->em->flush();
    }

    public function testTwoKids()
    {
        $c = $this->em->getRepository('AppBundle:Category')->findOneBy(['name' => 'Hook']);
        $cat = new \AppBundle\Entity\Category();
        $cat->setName('Wet');
        $this->em->persist($cat);
        $c->addChild($cat);
        $this->em->persist($c);
        $this->em->flush();

        /* this returns 1 */
        $c2 = $this->em->getRepository('AppBundle:Category')->findOneBy(['name' => 'Hook']);
        $children = $c2->getChildren();
        $this->assertEquals(2, count($children));

        /* this returns 2 */
//        $id = $c2->getId();
//        $children = $this->em->createQuery("SELECT c FROM AppBundle:Category c WHERE c.parent = $id")
//                ->getResult();
//       $this->assertEquals(2, count($children));

            }

【问题讨论】:

  • 我想你会发现这是你的测试中的一个错误。我不能完全理解正在发生的事情,但这可能是 Doctrine 结果缓存的问题。那里涉及到两个许多因素,以将其与 Doctrine 隔离开来。实体定义看起来不错。虽然addChildren() 方法有点奇怪。尝试在最后一次刷新后运行$this->em->clear();
  • @Ryan 太好了! $this->em->clear(); 解决了这个问题。作为解决方案发布,我很乐意接受。顺便说一句,addChildren() 是使用doctrine:generate:entity 的神器。

标签: php symfony doctrine-orm many-to-one


【解决方案1】:

在最后一次刷新之后尝试运行$this->em->clear()。这可能是由 Doctrine 实体管理器缓存或结果缓存引起的。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-12-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多