自己参照連想(隣接リスト)をプロパティ "children"の形で持つ "InterestGroup"というエンティティがあります1対多)と「親」(多対1)の2種類があります。Symfony Entityフィールドタイプクエリビルダの節が1対多の自己参照の関連付けで機能しない
InterestGroupのフォームタイプを設定する際に、すべての「トップレベル」の関心グループ(「parent」プロパティがnullのグループ)の選択肢を持つ、プロパティの親の選択リストを提供しようとしています。 EntityTypeフィールドのquery_builderにwhere句とnullパラメータを追加すると、いくつかのトップレベル(親がnullです)の関心グループが保持されていても、常に何も返されません。 where句を削除すると、テーブル内のすべてのInterestGroupsが返されます。 where節がなぜ機能していないのかを理解するのが難しいです。
->add('parent',EntityType::class,
array(
'placeholder' => 'Top Level (No Parent)',
'required' => false,
'class' => 'Common\ContentBundle\Entity\InterestGroup',
'query_builder' => function (EntityRepository $er) {
return $er->createQueryBuilder('ig')
->where('ig.parent = :n')
->setParameter('n',null)
->orderBy('ig.title', 'ASC');
},
'choice_label' => 'title'
)
)
上記空の選択メニューを返します。
これは、問題のフィールドがあります。 where句とsetparameterを削除することで、nullの親を持つすべてのInterestGroup Entitiesを取得します。続き
はInterestGroupのためのエンティティークラス
<?php
namespace Common\ContentBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use Doctrine\Common\Collections\ArrayCollection;
use Symfony\Component\Validator\Constraints as Assert;
use Gedmo\Mapping\Annotation as Gedmo;
/**
* InterestGroup
*
* @ORM\Table(name="interest_group")
* @ORM\Entity(repositoryClass="Common\ContentBundle\Repository\InterestGroupRepository")
*/
class InterestGroup
{
/**
* @var int
*
* @ORM\Column(name="id", type="integer")
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
*/
private $id;
/**
* @var string
*
* @ORM\Column(name="title", type="string", length=255, unique=true)
* @Assert\NotBlank(message="This is a required field.")
*/
private $title;
/**
* @ORM\OneToMany(targetEntity="InterestGroup", mappedBy="parent")
*/
private $children;
/**
* @ORM\ManyToOne(targetEntity="InterestGroup", inversedBy="children")
* @ORM\JoinColumn(name="parent_id", referencedColumnName="id")
*/
private $parent;
/**
* @Gedmo\Slug(fields={"title"})
* @ORM\Column(length=128, unique=true)
*/
private $slug;
// ...
/**
* @ORM\ManyToMany(targetEntity="Product", mappedBy="interestGroups")
*/
private $products;
/**
* InterestGroup constructor.
*/
public function __construct()
{
$this->children = new ArrayCollection();
$this->products = new ArrayCollection();
}
/**
* Get id
*
* @return int
*/
public function getId()
{
return $this->id;
}
/**
* @return string
*/
public function getTitle()
{
return $this->title;
}
/**
* @param string $title
*/
public function setTitle($title)
{
$this->title = $title;
}
/**
* @return mixed
*/
public function getSlug()
{
return $this->slug;
}
/**
* @return mixed
*/
public function getChildren()
{
return $this->children;
}
/**
* @param mixed $children
*/
public function setChildren($children)
{
$this->children = $children;
}
/**
* @return mixed
*/
public function getParent()
{
return $this->parent;
}
/**
* @param mixed $parent
*/
public function setParent($parent)
{
$this->parent = $parent;
}
/**
* @return mixed
*/
public function getProducts()
{
return $this->products;
}
}
、フォームタイプクラスです:事前に
<?php
namespace Common\ContentBundle\Form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Bridge\Doctrine\Form\Type\EntityType;
use Doctrine\ORM\EntityRepository;
class InterestGroupType extends AbstractType
{
/**
* @param FormBuilderInterface $builder
* @param array $options
*/
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('title',TextType::class)
->add('parent',EntityType::class,
array(
'placeholder' => 'Top Level (No Parent)',
'required' => false,
'class' => 'Common\ContentBundle\Entity\InterestGroup',
'query_builder' => function (EntityRepository $er) {
return $er->createQueryBuilder('ig')
->where('ig.parent = :n')
->setParameter('n',null)
->orderBy('ig.title', 'ASC');
},
'choice_label' => 'title'
)
)
;
}
/**
* @param OptionsResolver $resolver
*/
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'Common\ContentBundle\Entity\InterestGroup'
));
}
}
ありがとう!