2016-12-15 154 views
0

我有兩個MySQL表和相應的實體:如何創建一個Doctrine子查詢?

Question 
-------- 
id 
text 
level 


Asked 
-------- 
* @ORM\ManyToOne(targetEntity="QuestionEntity") 
* @ORM\JoinColumn(name="question", referencedColumnName="id") 
question 
user 

我想查詢具有特定水平和問題的所有問題尚未從給定用戶的詢問。我如何使用實體管理器查詢構建器來做到這一點? 隨着MySQL的句法的查詢是:

SELECT 
    * 
FROM 
    Question 
WHERE 
    Question.level = 1 
    AND Question.id NOT IN(SELECT Asked.question FROM Asked WHERE Asked.user = 23) 

我試過許多東西像托馬斯Madeyski評論,但我還是得到了500內部服務器錯誤。這是我的代碼:(我測試的子查詢,當它被孤立的感覺不錯)

$em = $this->getDoctrine()->getManager(); 
    $fbUser = $em->getRepository(FbUserEntity::class)->findOneBy(['fbId' => $session->get('fb_user_id')]); 

$qb = $em->createQueryBuilder(); 
$qb2 = $qb; 

$questions = $qb->select('q') 
    ->from('MyBundle:QuestionEntity', 'q') 
    ->where('q.level = :level') 
    ->setParameter('level', $level) 
    ->andWhere($qb->expr()->notIn(
     'q.id', 
     $qb2->select('a.question') 
      ->from('LMyBundle:AskedEntity', 'a') 
      ->where('a.user = :userid') 
      ->setParameter('userid', $fbUser->getId()) 
      ->getDQL() 
    )) 
    ->getQuery() 
    ->getResult(); 
+0

你會得到什麼錯誤? –

+0

HTTP 500錯誤: 糟糕!發生錯誤 服務器返回了「500內部服務器錯誤」。最糟糕的是我沒有收到任何錯誤信息,所以我不知道發生了什麼問題。 – ACs

+1

你應該檢查你的日誌以瞭解實際上錯誤 –

回答

0

嘗試是這樣的:

$qb = $em->createQueryBuilder(); 
$subQuery = $qb->select('a.question') 
    ->from('YourBundle:Asked', 'a') 
    ->andWhere('a.user = 23') 


$query = $qb->select('q') 
    ->from('YourBundle:Question', 'q') 
    ->andWhere('q.level = 1') 
    ->andWhere($qb->expr()->notIn('q.id', $subQuery->getDQL()) 
    ->getQuery() 
    ->getResult() 

這裏的關鍵是$qb->expr()->notIn()部分

0

調查日誌我想出了,而不是

$qb = $em->createQueryBuilder(); 
$qb2 = $qb; 

我應該創建一個新的queryBuilder對於qb2:

$qb = $em->createQueryBuilder(); 
$qb2 = $em->createQueryBuilder(); 

但是,這仍然給我一個錯誤。經過一番experimentingI想通了,如果執行子查詢,它給這樣的格式:

array (size=2) 
    0 => 
    array (size=1) 
     'question' => int 1 
    1 => 
    array (size=1) 
     'question' => int 2 

於是我運行通過子查詢的結果是這樣的:

$alreadyAsked = []; 
foreach($asked as $q){ 
    $alreadyAsked[] = $q['question']; 
} 

而且通過$ alreadyAsked數組這樣的主要查詢,那麼它的工作原理:

->andWhere($qb->expr()->notIn('q.id', $alreadyAsked))