Symfony + Sonata,一对多关系

Posted

技术标签:

【中文标题】Symfony + Sonata,一对多关系【英文标题】:Symfony + Sonata, OneToMany Relation 【发布时间】:2015-08-12 19:03:03 【问题描述】:

有人可以帮帮我吗?

我需要使用 Sonata admin bundle 实现书籍和读者列表。

问题是我为列表中的每个读者获得了空的已读书籍列。

外键可以写入数据库。

请看代码:

ReadersAdmin 类

protected function configureFormFields(FormMapper $formMapper)

    $formMapper
        ->add('name')
        ->add('book',
            'entity',
            array(
                'class'    => 'AppBundle:Books',
                'property' => 'name',
                'multiple' => true,
                'expanded' => true
            )
        );


/**
 * @param \Sonata\AdminBundle\Show\ShowMapper $showMapper
 *
 * @return void
 */
protected function configureShowField(ShowMapper $showMapper)

    $showMapper
        ->add('name')
        ->add('book')
    ;


/**
 * @param \Sonata\AdminBundle\Datagrid\ListMapper $listMapper
 *
 * @return void
 */
protected function configureListFields(ListMapper $listMapper)

    $listMapper
        ->add('name')
        ->add('book')
        ->add('_action', 'input', array(
            'actions' => array(
                'show' => array(),
                'edit' => array(),
                'delete' => array(),
            )
        ))
    ;

ReadersRelations 实体

 class ReadersRelations

    /**
     * @var integer
     *
     * @ORM\Column(name="id", type="integer")
     * @ORM\Id
     * @ORM\GeneratedValue(strategy="AUTO")
     */
    private $id;

    /**
     * @var Books
     *
     * @ORM\ManyToOne(targetEntity="\AppBundle\Entity\Books", inversedBy="ReadersRelations")
     * @ORM\JoinColumn(name="book_id", referencedColumnName="id")
     */
    private $book;

    /**
     * @var Readers
     *
     * @ORM\ManyToOne(targetEntity="\AppBundle\Entity\Readers", inversedBy="ReadersRelations")
     * @ORM\JoinColumn(name="reader_id", referencedColumnName="id")
     */
    private $reader;

图书实体

    <?php

namespace AppBundle\Entity;

use Doctrine\ORM\Mapping as ORM;
use Doctrine\Common\Collections\ArrayCollection;
/**
 * Books
 *
 * @ORM\Entity
 * @ORM\Table(name="Books")
 */
class Books

    /**
     * @var integer
     *
     * @ORM\Column(name="id", type="integer")
     * @ORM\Id
     * @ORM\GeneratedValue(strategy="AUTO")
     *
     */
    private $id;

    /**
     * @var string
     *
     * @ORM\Column(name="name", type="string", length=255)
     */
    private $name;

    /**
     * @var string
     *
     * @ORM\Column(name="author", type="string", length=255)
     *
     */
    private $author;

    /**
     * @var ReadersRelations
     *
     * @ORM\OneToMany(targetEntity="\AppBundle\Entity\ReadersRelations" , mappedBy="Books" , cascade="all")
     */
    private $readers;

    public function __toString()
    
        return $this->name;
    

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

    /**
     * Set name
     *
     * @param string $name
     * @return Books
     */
    public function setName($name)
    
        $this->name = $name;

        return $this;
    

    /**
     * Get name
     *
     * @return string 
     */
    public function getName()
    
        return $this->name;
    

    /**
     * Set author
     *
     * @param string $author
     * @return Books
     */
    public function setAuthor($author)
    
        $this->author = $author;

        return $this;
    

    /**
     * Get author
     *
     * @return string 
     */
    public function getAuthor()
    
        return $this->author;
    

读者实体

    <?php

    namespace AppBundle\Entity;

    use Doctrine\ORM\Mapping as ORM;
    use Doctrine\Common\Collections\ArrayCollection;
    use AppBundle\Entity\ReadersRelations;
    /**
     * Readers
     *
     * @ORM\Entity
     * @ORM\Table(name="Readers")
     */
    class Readers
    
        /**
         * @var integer
         *
         * @ORM\Column(name="id", type="integer")
         * @ORM\Id
         * @ORM\GeneratedValue(strategy="AUTO")     *
         */
        private $id;

        /**
         * @var string
         *
         * @ORM\Column(name="name", type="string", length=255)
         *      */
        private $name;

        /**
         * @var ReadersRelations
         *
         * @ORM\OneToMany(targetEntity="\AppBundle\Entity\ReadersRelations" , mappedBy="Readers" , cascade="all")
         */
        private $book;

        private $books;

        public function __construct()
        
            $this->book = new ArrayCollection();
            $this->books = new ArrayCollection();

        

        public function __toString()
        
            return $this->name;
        

        public function getBook()
        
            $books = new ArrayCollection();

            foreach($books as $p)
            
                $books[] = $p->getBook();
            

            return $books;
        

        public function setBook($books)
        
            foreach($books as $p)
            
                $po = new ReadersRelations();

                $po->setBook($p);
                $po->setReader($this);

                $this->addPo($po);
            

        

        public function addPo($ProductOrder)
        
            $this->book[] = $ProductOrder;
        

        public function removePo($ProductOrder)
        
            return $this->book->removeElement($ProductOrder);
        
    class Readers
    
        /**
         * @var integer
         *
         * @ORM\Column(name="id", type="integer")
         * @ORM\Id
         * @ORM\GeneratedValue(strategy="AUTO")     *
         */
        private $id;

        /**
         * @var string
         *
         * @ORM\Column(name="name", type="string", length=255)
         *      */
        private $name;

        /**
         * @var ReadersRelations
         *
         * @ORM\OneToMany(targetEntity="\AppBundle\Entity\ReadersRelations" , mappedBy="Readers" , cascade="all")
         */
        private $book;

        private $books;


        public function __construct()
        
            $this->book = new ArrayCollection();
            $this->books = new ArrayCollection();

        

        public function __toString()
        
            return $this->name;
        

        public function getBook()
        
            $books = new ArrayCollection();

            foreach($books as $p)
            
                $books[] = $p->getBook();
            

            return $books;
        

        public function setBook($books)
        
            foreach($books as $p)
            
                $po = new ReadersRelations();

                $po->setBook($p);
                $po->setReader($this);

                $this->addPo($po);
            

        

        public function addPo($ProductOrder)
        
            $this->book[] = $ProductOrder;
        
    /**
     * Get id
     *
     * @return integer 
     */
    public function getId()
    
        return $this->id;
    

    /**
     * Set name
     *
     * @param string $name
     * @return Readers
     */
    public function setName($name)
    
        $this->name = $name;

        return $this;
    

    /**
     * Get name
     *
     * @return string 
     */
    public function getName()
    
        return $this->name;
    

【问题讨论】:

【参考方案1】:

那么,您对使用您的关系存储数据有问题吗?或者只是为了获取列表中的数据?

如果是为了保存数据,尝试实现Sonata type collection或Sonata type model字段类型来注册新的相关条目。

然后,如果您有任何问题,我们将检查您的实体设置器是否缺少操作。

【讨论】:

以上是关于Symfony + Sonata,一对多关系的主要内容,如果未能解决你的问题,请参考以下文章

Sonata Admin Bundle:按计数一对多关系排序

将 sonata_type_collection 用于一对多一关系的问题

Symfony2 和 Doctrine:一对多关系

一对多、自引用关系 Symfony

Sonata Admin:显示动作而不是编辑的一对多路线

Symfony 2 与 Doctrine 中的一对多关系