2017-08-17 65 views
2

我有與用戶表中的多對多關係的實體:(使用選擇2)選擇Symfony的QueryBuilder的:太多的疑問

/** 
* @ORM\ManyToMany(targetEntity="User") 
* @ORM\JoinTable(
* name="offer_allowedusers", 
* joinColumns={ 
*  @ORM\JoinColumn(name="offer_id", referencedColumnName="id", onDelete="CASCADE") 
* }, 
* inverseJoinColumns={ 
*  @ORM\JoinColumn(name="user_id", referencedColumnName="id", onDelete="CASCADE") 
* } 
*) 
*/ 
private $allowedUsers; 

而且,在形式,我想顯示一個下拉列表,其允許用戶:

enter image description here

爲了做到這一點,我做了,形式建設:

->add('allowedUsers', EntityType::class, [ 
     'class' => 'AppBundle\Entity\User', 
     'query_builder' => function (EntityRepository $er) { 
      return $er->createQueryBuilder('u') 
      ->orderBy('u.username', 'ASC'); 
     }, 
     'label' => 'Allowed users', 
     'required' => false, 
     'multiple' => true 
    ]) 

的問題是,它使每個用戶的查詢,來獲取用戶名。所以,如果我有500個用戶,這讓500個查詢...

enter image description here

如何優化和做一個單一的查詢來獲取所有的記錄?

+0

您是否在User類中實現了__toString()方法?這個方法會返回我有的用戶名 – Mz1907

+0

,返回'$ this-> username'。沒有它,它不會在下拉菜單中顯示用戶名 –

+0

您是否嘗試在表單構建器選項數組中添加「'choice_label'=>'用戶名'? –

回答

4

明確創建在您的QueryBuilder中加入,並選擇用戶和允許的用戶。

UPDATE

還必須加入並選擇用戶配置文件和用戶設置OneToOne的關係,因爲教義自動檢索OneToOne關係他們你獲取用戶實體的任何時間。

Doctrine documentation talks about爲什麼在獲取一對一關係的反面時必須執行額外的查詢。

->add('allowedUsers', EntityType::class, [ 
    'class' => 'AppBundle\Entity\User', 
    'query_builder' => function (EntityRepository $er) { 
     return $er->createQueryBuilder('u') 
      ->select('u, au, up, us') 
      ->join('u.allowedUsers', 'au') 
      ->join('u.userProfile', 'up') 
      ->join('u.userSettings', 'us') 
      ->orderBy('u.username', 'ASC') 
     ; 
    }, 
    'label' => 'Allowed users', 
    'required' => false, 
    'multiple' => true 
]) 
+0

你是一個天才:)順便說一句,刪除' - >加入('u.allowedUsers','au')行後,因爲該關係不存在(允許的用戶是相關的報價,而不是給用戶) –

+1

陷阱。是的OneToOne關係的東西絆了我很長一段時間,在一個極端的情況下,我改變了ORM模式,認爲它是OneToMany,但通過代碼仍然把它當作OneToOne。無論哪種方式加入是你的朋友:) –

1

如果沒有查詢到你的「實體」不需要獲取allowedUsers最簡單的方法是明確定義獲取模式EAGER領域的註解:

/** 
* @ORM\ManyToMany(targetEntity="User", fetch="EAGER") 
* @ORM\JoinTable(
* name="offer_allowedusers", 
* joinColumns={ 
*  @ORM\JoinColumn(name="offer_id", referencedColumnName="id", onDelete="CASCADE") 
* }, 
* inverseJoinColumns={ 
*  @ORM\JoinColumn(name="user_id", referencedColumnName="id", onDelete="CASCADE") 
* } 
*) 
*/ 
private $allowedUsers; 
+0

完成,但沒有任何變化 –