2017-04-19 88 views
1

我有一個CakePHP 3應用程序,它有2個模型,UrlsDownloads。這些模型是相關聯的,使得URL可以有多個下載(Cake中的Urls hasMany Downloads)。如何在CakePHP 3中分頁查詢子查詢?

當我做一個查詢像這樣它就會從Urls表中返回1行以及所有相關Downloads的:

// This is in a view() method 
$query = $this->Urls->find()->contain(['Downloads' => ['sort' => ['Downloads.created' => 'DESC'] ] ])->where(['id' => $id]); 

我想分頁的Downloads列表中,但無法看到如何做這個。我已經看到了在https://book.cakephp.org/3.0/en/controllers/components/pagination.html但我唯一能找到的東西,我試過是:

public function initialize() 
{ 
    parent::initialize(); 
    $this->loadComponent('Paginator'); 
} 

// In my view() method 
$this->paginate = [ 
    'contain' => ['Downloads'] 
]; 

$query = $this->Urls->find()->contain(['Downloads' => ['sort' => ['Downloads.created' => 'DESC'] ] ])->where(['id' => $id])->paginate(); 

,但它只是錯誤說 未知法「拼版」

+0

您可能希望再次仔細閱讀文檔,'paginate()'方法不是表類的方法。 – ndm

回答

0

既然你是隻顯示一行網址你可以做兩個查詢。

一個查詢中獲取的網址(不下載)

$url = $this->Urls->get($id); 

第二個取回(和分頁!)的dowloads

$downloads = $this->Urls->Downloads->find() 
    ->sort(['created' => 'DESC']) 
    ->where(['url_id' => $id]); 

$downloads = $this->paginate($downloads) 
+0

我真的希望在1個查詢中完成所有工作,因爲能夠使用'contains'的要點是你*不必*做單獨的查詢。謝謝你的信息。 – Andy

+1

蛋糕最終會做兩個不同的查詢來檢索數據。所以我沒有看到這一點 – arilia

0

由於下載所屬的網址,你可以做相反,如下所示:

$downloads = $this->Urls->Downloads->find() 
    ->contain('Urls') 
    ->where(['url_id' => $id]) 
    ->order(['created' => 'DESC']); 
0

您的錯誤是因爲paginate()不符合表類的hod,並且你在表對象上調用它,所以它是未知的。你需要把它的控制器對象: -

$this->paginate(); 

作爲paginate是一個控制器方法,因爲你是在你的榜樣嘗試它不能被稱爲查詢檢索的Url的一部分。這意味着您需要執行兩個查詢,但這是CakePHP如果包含下載內容就會失敗的問題。例如: -

$this->Urls->get($id, ['contain' => 'Downloads']); 

這實質上導致以下兩個查詢,因爲它不能在SQL中使用JOIN完成: -

$this->Urls->get($id); 
$this->Urls->Downloads->find('all')->where(['url_id' => $id])->all(); 

所以,你需要得到Url第一: -

$url = $this->Urls->get($id); 

然後進行分頁要對下載的查找查詢傳遞到您的PAGINATE方法下載: -

$query = $this->Urls->Downloads->find() 
    ->sort(['created' => 'DESC']) 
    ->where(['url_id' => $id]); 
$downloads = $this->paginate($query);