Symfony2 Form Builder Select Across Join Table with Metadata

后端 未结 3 2043
广开言路
广开言路 2021-02-03 12:40

I have 3 entities:

[Member] ----OneToMany----> [MemberCategory] ---ManyToOne---> [Category]

This works well as far as fetching results fr

相关标签:
3条回答
  • 2021-02-03 13:12

    You will need to use the querybuilder inside your form

    $builder->add('categories', 'entity', array(
            'class' => 'SMWMemberBundle:MemberCategory',
            'property'     => 'category.categoryName',
            'query_builder' => function(EntityRepository $er ) use ( ? ) {
               return $er->createQueryBuilder( ? )
    
              // your query with a left join probably
    
             }
            'multiple'     => true,
            'expanded'     => true,
            'required' => false
        ));
    

    See documentation for proper use. see symfony2 form querybuilder with parameters for an exmple

    0 讨论(0)
  • 2021-02-03 13:16

    The post of cheesemacfly is not so bad, but it is call embeded form and can be complicated to manage. In fact, you jus need to create a "Custom Repositories" http://symfony.com/doc/current/book/doctrine.html#custom-repository-classes

    It will add a new methods for "grabbing" your ORM object with Doctrine2 like find() or findBy();

    1) Create a new repository in a Repository Folder of your Bundle

    <?php
      namespace YourVendor\SMWMemberBundle\Repository;
      use Doctrine\ORM\EntityRepository;
    
      class CategoryRepository extends EntityRepository{
    
      public function UsedByMember($member){
      return $this
             ->createQueryBuilder('c')
             ->leftJoin('c.Member', 'mc')
             ->where('mc.member = ?1')
             ->setParameter(1, $member);
    }
    

    }

    2) Attached your Cutom repository to your Entity

    namespace YourVendor\SMWMemberBundle\Entity;
    use Doctrine\ORM\Mapping as ORM;
    
    /**
    * @ORM\Entity(repositoryClass="YourVendor\SMWMemberBundle\Entity\ProductRepository")
    * @ORM\Table(name="Category") 
    */
    class Category{
    

    3) add a constructor to your Form class and pass de Entity Manager and the variable required to your query :

    class CategoryUserForm extends AbstractType
    {
       private $em;
       private $member ;
    
    
       public function __construct(EntityManager $em, $site, $seed)
       {
           $this->em = $em;
           $this->member = $member;
    
       }
    
    public function buildForm(FormBuilder $builder, array $options)
    {
        $qb = $this->em->getRepository('SMWMemberBundle:Category')->UsedByUsers($this->member);
        $builder->add('categories', 'entity', array(
            'class' => 'SMWMemberBundle:MemberCategory',
            'query_builder'     => $qb,
            'multiple'     => true,
            'expanded'     => true,
            'required' => false
        ));
     }
    

    4) In your controller, you create your form like that :

    $editForm = $this->createForm(new CategoryUserForm($em, $member), $category);
    

    Feel free to ask me questions, I'm hope this is what you are looking for ;)

    0 讨论(0)
  • 2021-02-03 13:30

    This is how I resolved this problem in the past (applied to your example) but this is what I figured out so it might not be 100% right for your case.

    First create a MemberCategory form type matching your needs:

    <?php    
    namespace Company\YourBundle\Form\Type;
    
    use Symfony\Component\Form\AbstractType;
    use Symfony\Component\Form\FormBuilderInterface;
    use Symfony\Component\OptionsResolver\OptionsResolverInterface;
    
    class MemberCategoryType extends AbstractType
    {
        public function buildForm(FormBuilderInterface $builder, array $options)
        {
            $builder
                ->add('priority')
                ->add('category', 'entity',
                        array('property' => 'name',
                            'class' => 'CompanyYourBundle:Category'))
            ;
        }
    
        public function setDefaultOptions(OptionsResolverInterface $resolver)
        {
            $resolver->setDefaults(array(
                'data_class' => 'Company\YourBundle\Entity\MemberCategory'
            ));
        }
    
        public function getName()
        {
            return 'company_yourbundle_membercategorytype';
        }
    }
    

    Then add this form type inside your Member type form:

    <?php
    
    namespace Company\YourBundle\Form\Type;
    
    use Symfony\Component\Form\AbstractType;
    use Symfony\Component\Form\FormBuilderInterface;
    use Symfony\Component\OptionsResolver\OptionsResolverInterface;
    
    class MemberType extends AbstractType
    {
        public function buildForm(FormBuilderInterface $builder, array $options)
        {
            $builder
                ->add('name')
                ->add('members', 'collection', array(
                    'type' => new MemberCategoryType(),
                    'allow_add' => true,
                    'allow_delete' => true,
                    'by_reference' => false,));
            ;
        }
    
        public function setDefaultOptions(OptionsResolverInterface $resolver)
        {
            $resolver->setDefaults(array(
                'data_class' => 'Company\YourBundle\Entity\Member'
            ));
        }
    
        public function getName()
        {
            return 'company_yourbundle_membertype';
        }
    }
    

    Then you can follow the documentation to add as many categories as you want to your members and assigning a priority every time.

    0 讨论(0)
提交回复
热议问题