ArrayCollection:在窗体中检索集合 [英] ArrayCollection: retrive collection in a form
问题描述
我用Symfony2制作了一个Web应用程序,其中一个用户与Mission实体有一个数组关联ManytoMany。用户可以通过表单上传实体$ product,并且表单传递的其中一个数据是与用户关联的任务。
每个用户不止有一项任务,所以,当他上传一个$ product对象时,他也应该能够选择他喜欢的任务。
要上传文件,我在控制器中使用一个表单以下方式:
$ form = $ this-> createFormBuilder($ product)
- > add(' ('required'=> true,'multiple'=> false,'class'=>'AcmeManagementBundle:Mission','query_builder'=> function($ repository){return $ repository-> createQueryBuilder('c') - > orderBy('c.id','ASC');},))
// ...
- > add('保存','提交')
- > getForm();
它可以工作,但不是很好:事实上,在这个领域,我可以选择所有存储的任务,而不是只有与用户关联的那些。
我试过了:
$ form = $ this- > createFormBuilder($ product)
- > add('mission','collection',array('required'=> true))
// ...
- > ; add('save','submit')
- > getForm();
它可以工作,但只显示一个任务,并且不允许用户选择首选任务。
我也试过:
- > add(' ('required'=> true))
但它告诉我:
属性任务和方法getMissions(),
isMissions ),hasMissions(),__get()存在并且在类Acme \ GlobeStoreBundle \Entity\Product中具有公共访问权限
。
我该如何更换控制器?
我的产品实体是:
class产品
{
/ **
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ ORM\OneToMany(targetEntity =Acme\ManagementBundle\Entity\Mission,mappedBy =product )
* /
保护$任务;
// ...
/ **
*设置任务
*
* @param字符串$任务
* @返回产品
* /
公共功能setMission($ mission)
{
$ this-> mission = $ mission;
返回$ this;
$ b / **
*获取任务
*
* @return string
* /
public function getMission( )
{
return $ this-> mission;
}
// ...
更新---
我将发布我的产品和任务实体,如评论中所述
这是我的用户实体是:
抽象类用户扩展BaseUser
{
$ b $ / **
* @ var \Doctrine\Common\Collections\ArrayCollection
*
* @ ORM\ManyToMany(targetEntity =Acme\ManagementBundle\Entity\Mission,inversedBy =users, orphanRemoval = true)
* @ ORM\JoinTable(name =user_mission)
* /
private $ missions;
/ **
*增加任务
*
* @param \Acme\ManagementBundle\Entity\Mission $任务
* @返回用户
* /
public function addMission(\Acme\ManagementBundle\Entity\Mission $ missions)
{
$ this-> missions [] = $ missions;
返回$ this;
}
// ...
我的任务实体: p>
<?php
命名空间Acme \ManagementBundle \Entity;
使用Doctrine \ORM\Mapping作为ORM;
使用Doctrine\Common\Collections\ArrayCollection;
使用Doctrine\Common\Collections\Collection;
/ **
* @ ORM\Entity
* /
class Mission {
/ **
* @ ORM \ Id
* @ ORM\GeneratedValue
* @ ORM\Column(type =integer)
* @var整数
* /
保护$ id;
/ **
* @ ORM\Column(type =string,length = 60)
* @var String
* /
protected $ name;
/ **
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ ORM\ManyToOne(targetEntity =Acme\GroundStationBundle\\ );
* @ ORM \JoinColumn(name =productId,referencedColumnName =id)
* /
private $ product;
/ **
* @ ORM\Column(type =string,length = 600)
* @var String
* /
protected $ description;
/ **
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ ORM\ManyToMany(targetEntity =Acme\ManagementBundle\\ \\ Entity \ User,mappedBy =tasks,cascade = {all},orphanRemoval = true)
* /
private $ users;
public function __construct(){
$ this - > users = new ArrayCollection();
$ b $ **
*获取id
*
* @return整数
* /
public function getId( )
{
return $ this-> id;
$ b / **
*名称
*
* @param字符串$名称
* @return Mission
* /
public function setName($ name)
{
$ this-> name = $ name;
返回$ this;
$ b / **
*获取名称
*
* @return字符串
* /
public function getName )
{
return $ this-> name;
}
$ b / **
*设置描述
*
* @param字符串$描述
* @return任务
* /
public function setDescription($ description)
{
$ this-> description = $ description;
返回$ this;
$ b / **
*获取描述
*
* @return string
* /
public function getDescription( )
{
return $ this-> description;
}
/ **
*添加用户
*
* @param \Acme\ManagementBundle\Entity\User $ users
* @return Mission
* /
public function addUser(\Acme\ManagementBundle\Entity\User $ users)
{
$ this-> users [] = $ users;
返回$ this;
}
/ **
*删除用户
*
* @param \Acme\ManagementBundle\Entity\User $ users
* /
public function removeUser(\Acme\ManagementBundle\Entity\User $ users)
{
$ this-> users-> removeElement($ users );
}
/ **
*获取用户
*
* @return \Doctrine\Common\Collections\Collection
* /
public function getUsers()
{
return $ this-> users;
}
public function __toString()
{
return $ this-> name;
}
/ **
*设置产品
*
* @param \Acme\GroundStationBundle\Entity\Product $ product
* @return Mission
* /
公共功能setProduct(\Acme\GroundStationBundle\Entity\Product $ product = null)
{
$ this-> product = $产品;
返回$ this;
}
/ **
*获取产品
*
* @return \Acme\GroundStationBundle\Entity\Product
* /
public function getProduct()
{
return $ this-> product;
}
}
看看我对代码的修改。
当你定义一个(产品)ToMany(任务)关系时,你有这样的情况:
1。产品具有许多任务,并且必须具有任务的ArrayCollection,您可以添加,移除或获取所有任务。
class Product
{
/ **
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ ORM \OneToMany(targetEntity =Acme \ManagementBundle\Entity\Mission,mappedBy =product)
* /
//将此属性重命名为复数。产品有许多任务
//比命名约定是人类可读的addMission和removeMission从收集但getMissions
保护$任务;
// ...
//
//删除这些函数:
public function setMission($ mission)
// ...
public function getMission()
// ...
//
//添加这些函数:
public function __construct(){
$ this-> missions = new ArrayCollection();
}
公共职能addMission(Acme \ManagementBundle\Entity\Mission $ mission)
{
$ this->任务[] = $任务;
返回$ this;
}
public function removeMission(Acme \ManagementBundle\Entity\Mission $ mission)
{
$ this-> missions-> removeElement( $ mission);
返回$ this;
}
public function getMissions()
{
return $ this-> missions;
}
// ...
2。强大>许多使命都属于一种产品。只更改注释
class Mission {
// ...
// RENAME inversedBy to missions
/ **
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ ORM\ManyToOne(targetEntity =Acme\GroundStationBundle\ )
* @ ORM \JoinColumn(name =productId,referencedColumnName =id)
* /
private $ product;
编辑开始
3。相反 - 很多产品属于一个任务
如果您在评论中提到了类似的情况,那么您的注释是错误的。看看这个修正:
class Product
{
// ...
/ **
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ ORM\ManyToOne(targetEntity =Acme\GroundStationBundle\Entity\Mission ,inversedBy =products)
* @ ORM\JoinColumn(name =missionId,referencedColumnName =id)
* /
protected $ mission;
// ...
//回滚这个函数:
public function setMission($ mission)
public function getMission()
//删除这些函数
public function __construct(){
public function addMission(Acme \ManagementBundle\Entity\Mission $ mission)
public function removeMission( Acme\\ManagementBundle\\Entity\Mission $ mission)
public function getMissions()
// ...
class Mission {
// ...
/ **
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ ORM\OneToMany (targetEntity =Acme \ManagementBundle\Entity\Product,mappedBy =mission)
* /
private $ products;
// ...
//
//删除这些函数:
public function setProduct($ product)
public function getProduct()
// ...
//
//添加这些函数:
public function __construct(){
$ this-> ; products = new ArrayCollection();
}
public function addProduct(Acme \ManagementBundle\Entity\Product $ product)
{
$ this-> products [] = $ product ;
返回$ this;
}
public function removeProduct(Acme \ManagementBundle\Entity\Product $ product)
{
$ this-> products-> removeElement( $ product);
返回$ this;
}
public function geProducts()
{
return $ this-> products;
}
// ...
编辑结束 3。之后,请记住: 祝您好运! I made a web application with Symfony2, in which a User has an array correlation ManytoMany with the entity Mission. The User can upload the entity $product through a form, and one of the data passed by the form is the mission associated to the user. There are more than only one mission for every user; so, when he uploads a $product object, he should also be able to select the mission he prefers. To upload the file I use a form in a controller in the following way: It works, but not fine: indeed in this field I can select all the mission stored, and not only the ones associated with the user. I tried then with: It works but shows only one mission, and doesn't allow the user to select the preferred mission. I tried also with: but it tells me: How I should change my controller?? My product entity is: UPDATE --- I will post also my product and mission entity, as asked in the comments This is my User Entity is: And my Mission Entity:
Please take a look at my changes to your code. When you define One(product)ToMany(missions) relation you have situation like this: 1. Product has many missions and must have an ArrayCollection of missions which you can add, remove or get all. 2. Many MissionS are owned by one product. Change only annotation EDIT START 3. Opposite - MANY products Belongs to one Mission
If there is situation like you mentioned in comment, then your Annotations are wrong. Look at this fix: EDIT END 3. After that remember to: Good Luck! 这篇关于ArrayCollection:在窗体中检索集合的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!
< code $ php app / console doctrine:generate:entities AcmeGroundStationBundle:Product
$ php app / console doctrine:generate:entities AcmeGroundStationBundle:Mission
$ php app / console doctrine:schema:update - -force
$form = $this->createFormBuilder($product)
->add('mission', 'entity', array('required' => true, 'multiple' => false, 'class' => 'AcmeManagementBundle:Mission', 'query_builder' => function($repository) { return $repository->createQueryBuilder('c')->orderBy('c.id', 'ASC'); },))
//...
->add('save', 'submit')
->getForm();
$form = $this->createFormBuilder($product)
->add('mission', 'collection', array('required' => true) )
//...
->add('save', 'submit')
->getForm();
->add('mission', 'collection', array('required' => true) )
Neither the property "missions" nor one of the methods "getMissions()",
"isMissions()", "hasMissions()", "__get()" exist and have public access
in class "Acme\GroundStationBundle\Entity\Product".
class Product
{
/**
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ORM\OneToMany(targetEntity="Acme\ManagementBundle\Entity\Mission", mappedBy="product")
*/
protected $mission;
//...
/**
* Set mission
*
* @param string $mission
* @return Product
*/
public function setMission($mission)
{
$this->mission = $mission;
return $this;
}
/**
* Get mission
*
* @return string
*/
public function getMission()
{
return $this->mission;
}
//...
abstract class User extends BaseUser
{
/**
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ORM\ManyToMany(targetEntity="Acme\ManagementBundle\Entity\Mission", inversedBy="users", orphanRemoval=true)
* @ORM\JoinTable(name="user_mission")
*/
private $missions;
/**
* Add missions
*
* @param \Acme\ManagementBundle\Entity\Mission $missions
* @return User
*/
public function addMission(\Acme\ManagementBundle\Entity\Mission $missions)
{
$this->missions[] = $missions;
return $this;
}
//...
<?php
namespace Acme\ManagementBundle\Entity;
use Doctrine\ORM\Mapping as ORM;
use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection;
/**
* @ORM\Entity
*/
class Mission {
/**
* @ORM\Id
* @ORM\GeneratedValue
* @ORM\Column(type="integer")
* @var integer
*/
protected $id;
/**
* @ORM\Column(type="string", length=60)
* @var String
*/
protected $name;
/**
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ORM\ManyToOne(targetEntity="Acme\GroundStationBundle\Entity\Product", inversedBy="mission")
* @ORM\JoinColumn(name="productId", referencedColumnName= "id")
*/
private $product;
/**
* @ORM\Column(type="string", length=600)
* @var String
*/
protected $description;
/**
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ORM\ManyToMany(targetEntity="Acme\ManagementBundle\Entity\User", mappedBy="missions", cascade={"all"}, orphanRemoval=true)
*/
private $users;
public function __construct(){
$this -> users = new ArrayCollection();
}
/**
* Get id
*
* @return integer
*/
public function getId()
{
return $this->id;
}
/**
* Set name
*
* @param string $name
* @return Mission
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* Get name
*
* @return string
*/
public function getName()
{
return $this->name;
}
/**
* Set description
*
* @param string $description
* @return Mission
*/
public function setDescription($description)
{
$this->description = $description;
return $this;
}
/**
* Get description
*
* @return string
*/
public function getDescription()
{
return $this->description;
}
/**
* Add users
*
* @param \Acme\ManagementBundle\Entity\User $users
* @return Mission
*/
public function addUser(\Acme\ManagementBundle\Entity\User $users)
{
$this->users[] = $users;
return $this;
}
/**
* Remove users
*
* @param \Acme\ManagementBundle\Entity\User $users
*/
public function removeUser(\Acme\ManagementBundle\Entity\User $users)
{
$this->users->removeElement($users);
}
/**
* Get users
*
* @return \Doctrine\Common\Collections\Collection
*/
public function getUsers()
{
return $this->users;
}
public function __toString()
{
return $this->name;
}
/**
* Set product
*
* @param \Acme\GroundStationBundle\Entity\Product $product
* @return Mission
*/
public function setProduct(\Acme\GroundStationBundle\Entity\Product $product = null)
{
$this->product = $product;
return $this;
}
/**
* Get product
*
* @return \Acme\GroundStationBundle\Entity\Product
*/
public function getProduct()
{
return $this->product;
}
}
class Product
{
/**
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ORM\OneToMany(targetEntity="Acme\ManagementBundle\Entity\Mission", mappedBy="product")
*/
// RENAME this attribute to plural. Product HAS MANY missions
// Than naming convention is "human readable" addMission and removeMission from collection but getMissions
protected $missions;
//...
//
// remove those functions:
public function setMission($mission)
//...
public function getMission()
//...
//
// add those functions:
public function __construct(){
$this->missions = new ArrayCollection();
}
public function addMission( Acme\ManagementBundle\Entity\Mission $mission )
{
$this->missions[] = $mission;
return $this;
}
public function removeMission( Acme\ManagementBundle\Entity\Mission $mission )
{
$this->missions->removeElement( $mission );
return $this;
}
public function getMissions()
{
return $this->missions;
}
//...
class Mission {
//...
// RENAME inversedBy to missions
/**
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ORM\ManyToOne(targetEntity="Acme\GroundStationBundle\Entity\Product", inversedBy="missions")
* @ORM\JoinColumn(name="productId", referencedColumnName= "id")
*/
private $product;
class Product
{
// ...
/**
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ORM\ManyToOne(targetEntity="Acme\GroundStationBundle\Entity\Mission", inversedBy="products")
* @ORM\JoinColumn(name="missionId", referencedColumnName= "id")
*/
protected $mission;
// ...
// roll back this functions:
public function setMission($mission)
public function getMission()
// remove those functions
public function __construct(){
public function addMission( Acme\ManagementBundle\Entity\Mission $mission )
public function removeMission( Acme\ManagementBundle\Entity\Mission $mission )
public function getMissions()
//...
class Mission {
// ...
/**
* @var \Doctrine\Common\Collections\ArrayCollection
*
* @ORM\OneToMany(targetEntity="Acme\ManagementBundle\Entity\Product", mappedBy="mission")
*/
private $products;
// ...
//
// remove those functions:
public function setProduct($product)
public function getProduct()
//...
//
// add those functions:
public function __construct(){
$this->products = new ArrayCollection();
}
public function addProduct( Acme\ManagementBundle\Entity\Product $product )
{
$this->products[] = $product;
return $this;
}
public function removeProduct( Acme\ManagementBundle\Entity\Product $product )
{
$this->products->removeElement( $product );
return $this;
}
public function geProducts()
{
return $this->products;
}
//...
$ php app/console doctrine:generate:entities AcmeGroundStationBundle:Product
$ php app/console doctrine:generate:entities AcmeGroundStationBundle:Mission
$ php app/console doctrine:schema:update --force