[英]Yii - CActiveDataProvider using relations
I am trying to use relations as part of the criteria to create a CActiveDataProvider
. 我试图使用关系作为标准的一部分来创建
CActiveDataProvider
。 I have the following: 我有以下内容:
User model: 用户模型:
return array(
'favourites'=>array(self::HAS_MANY, 'UserFavourite', 'user_id', 'order'=>'added_at DESC'),
);
UserFavourite model: UserFavourite模型:
return array(
'user'=>array(self::BELONGS_TO, 'User', 'user_id'),
'listing'=>array(self::BELONGS_TO, 'Listing', 'listing_id'),
);
Controller (view favourites action): 控制器(查看收藏夹操作):
$user = $this->loadUser(Yii::app()->user->id);
How do I create a CActiveDataProvider
in my User model that fetches all favourites
by the current user - along with the related listing
model data for each favourite? 如何在我的用户模型中创建
CActiveDataProvider
,以获取当前用户的所有favourites
- 以及每个收藏夹的相关listing
模型数据? So I want to do something like $favourites = $user->getFavourites();
所以我想做一些像
$favourites = $user->getFavourites();
. 。
The CActiveDataProvider
should return an array of Listing
objects. CActiveDataProvider
应该返回一个Listing
对象数组。 It should support pagination and sorting - the default sort will be added_at DESC
. 它应该支持分页和排序 - 默认排序将是
added_at DESC
。
I have tried using the with
option of CDbCriteria
but that does not seem to work... 我尝试过使用
CDbCriteria
的with
选项,但这似乎不起作用......
You have not provided your database schema, but i guess this code could work, 您还没有提供数据库架构,但我想这段代码可以工作,
$criteria=new CDbCriteria();
$criteria->with=array('favourites'=>array('with'=>'listing'));
$dataProvider= new CActiveDataProvider('User', array(
'criteria'=>$criteria,
'sort'=>array(
'defaultOrder'=>'t.added_at DESC',
)));
Please make sure your Relations are correct and according to schema. 请确保您的关系正确且符合架构。
Infact, If you dont care about number of queries, you can always call something like 事实上,如果你不关心查询的数量,你可以随时调用类似的东西
$user->favourites; $用户>收藏夹;
It will return proper data for correct relations, Again you can do this 它将返回正确关系的正确数据,您可以再次执行此操作
In order to , pass listing model to view go like this 为了 ,通过列表模型查看就像这样
foreach($user->favourites as $fav){
$this->renderPartial("PATH TO YOUR VIEW",array('data'=>$fav->listing));
}
Note that there may be many Favourites for an user so you need to use foreach , unless you are not using CListview . 请注意,用户可能有许多收藏夹,因此您需要使用foreach,除非您不使用CListview 。 Another way is to user Clistview in that case you may need to change your query.Let me know how that works for you.
另一种方法是用户Clistview,在这种情况下,您可能需要更改您的查询。让我知道这对您有用。
In your Listing
relations
method you need to have the relations to Users
through the intermediate table UsersFavourite
. 在您的
Listing
relations
方法中,您需要通过中间表UsersFavourite
与Users
建立关系。 The relationship type is HAS_MANY: 关系类型是HAS_MANY:
return array(
'favourites'=>array(self::HAS_MANY, 'UserFavourite', 'listing_id'),
'users'=>array(self::HAS_MANY, 'User', array('user_id'=>'id'), 'through'=>'favourites')
);
In your User
method that returns the CActiveDataProvider
: The main model is Listing
, joined to UserFavourite
and User
. 在返回
CActiveDataProvider
的User
方法中:主模型是Listing
,加入UserFavourite
和User
。 You must set together
to true
to build one single sql query. 您必须设置
together
,以true
建立一个单一的SQL查询。 Finally you must set the users.id to the current id of User
model to bring only the rows relevant to the current user. 最后,您必须将users.id设置为
User
model的当前ID,以仅显示与当前用户相关的行。
$criteria = new CDbCriteria;
$criteria->with = array( 'favourites','users =>'array('condition'=>"users.id=:user_id"));
$criteria->together = true;
$criteria->params = array(':user_id'=>$this->id);
return new CActiveDataProvider('Listing', array(
'criteria'=>$criteria,
'sort'=>array('defaultOrder'=>'favourites.added_at DESC')
));
I tested this answer and worked correctly with a small dataset. 我测试了这个答案,并使用一个小数据集正确工作。
Here is how I have achieved the required output: 这是我如何达到所需的输出:
$criteria = new CDbCriteria;
$criteria->condition = 'uf.user_id = :user_id';
$criteria->params = array(':user_id'=>$this->id);
$criteria->join = 'LEFT OUTER JOIN user_favourite uf ON uf.listing_id = t.id';
$criteria->order = 'uf.added_at DESC';
return new CActiveDataProvider('Listing', array(
'criteria'=>$criteria,
));
In the end I have just hard-coded in the JOIN, rather than try and use the relation, as it seems it is not meant to work that way. 最后我在JOIN中进行了硬编码,而不是尝试使用关系,因为它似乎并不意味着以这种方式工作。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.