Php Yii关系记录与来自其他表的条件

Php Yii关系记录与来自其他表的条件,php,activerecord,yii,Php,Activerecord,Yii,我有一个类似于以下内容的关系记录: 存在ID为的用户(表用户) 有id为、名称为的类别(表类别) 有id为、正文为、类别为的文章(表格文章) 然后有一个表read\u articles,其中包含article\u id、user\u id 因此,用户可以看到一个类别中所有文章的列表。他们可以单击一篇文章,它将向read_articles表中添加一个条目(用户id、文章id) 我希望能够使用Yii的ActiveRecord获取当前用户尚未阅读的给定类别中的所有文章,并显示这些文章。我一直在从S

我有一个类似于以下内容的关系记录:

  • 存在ID为的用户(表用户)
  • 有id为、名称为的类别(表类别)
  • 有id为、正文为、类别为的文章(表格文章)
  • 然后有一个表read\u articles,其中包含article\u id、user\u id
因此,用户可以看到一个类别中所有文章的列表。他们可以单击一篇文章,它将向read_articles表中添加一个条目(用户id、文章id)

我希望能够使用Yii的ActiveRecord获取当前用户尚未阅读的给定类别中的所有文章,并显示这些文章。我一直在从SQL的角度考虑它,但我不确定如何将它应用到我的ActiveRecord设置中。我的第一个想法是在文章active record上设置一个参数化范围:

public function unread( $userId )
{
    $this->getDbCriteria()->mergeWith( array(
        'alias' => 'articles',
        'condition' => 'not exists (SELECT * '
            . 'FROM user_read_articles '
            . 'WHERE articles.id=user_read_articles.article_id '
            . 'AND read_articles.user_id=' . (int)$userId
            . ')',
    ) );
}
它似乎起作用了,但我觉得它真的很脏

有没有一种更干净的方法来完成我在ActiveRecord中所说的?或者我应该考虑向更简单的SQL和处理这样的事情我自己(但失去了很多好的特性的AR)?< /P> 编辑以下是上述模型的关系:(免责声明,这些模型仅被截断为相关部分)

用户活动记录

public function relations()
{
    return array(
        'categories' => array(
            self::HAS_MANY,
            'UserCategoryActiveRecord',
            'user_id' ),
        // I added this early using gii, never really used it...
        'readArticles' => array(
            self::HAS_MANY,
            'UserReadArticleActiveRecord',
            'user_id' ),
    );
}
public function relations()
{
    return array(
        'user' => array(
            self::BELONGS_TO,
            'UserActiveRecord',
            'user_id' ),
        'articles' => array(
            self::HAS_MANY,
            'ArticleActiveRecord',
            'category_id',
            'order' => 'articles.pub_date DESC' ),
    );
}
public function relations()
{
    return array(
        'category' => array(
            self::BELONGS_TO,
            'CategoryActiveRecord',
            'category_id' ),
    );
}
用户类别活动记录

public function relations()
{
    return array(
        'categories' => array(
            self::HAS_MANY,
            'UserCategoryActiveRecord',
            'user_id' ),
        // I added this early using gii, never really used it...
        'readArticles' => array(
            self::HAS_MANY,
            'UserReadArticleActiveRecord',
            'user_id' ),
    );
}
public function relations()
{
    return array(
        'user' => array(
            self::BELONGS_TO,
            'UserActiveRecord',
            'user_id' ),
        'articles' => array(
            self::HAS_MANY,
            'ArticleActiveRecord',
            'category_id',
            'order' => 'articles.pub_date DESC' ),
    );
}
public function relations()
{
    return array(
        'category' => array(
            self::BELONGS_TO,
            'CategoryActiveRecord',
            'category_id' ),
    );
}
ArticleActiveRecord

public function relations()
{
    return array(
        'categories' => array(
            self::HAS_MANY,
            'UserCategoryActiveRecord',
            'user_id' ),
        // I added this early using gii, never really used it...
        'readArticles' => array(
            self::HAS_MANY,
            'UserReadArticleActiveRecord',
            'user_id' ),
    );
}
public function relations()
{
    return array(
        'user' => array(
            self::BELONGS_TO,
            'UserActiveRecord',
            'user_id' ),
        'articles' => array(
            self::HAS_MANY,
            'ArticleActiveRecord',
            'category_id',
            'order' => 'articles.pub_date DESC' ),
    );
}
public function relations()
{
    return array(
        'category' => array(
            self::BELONGS_TO,
            'CategoryActiveRecord',
            'category_id' ),
    );
}
在构建这个模型的早期,我还制作了一个“UserReadArticleActiveRecord”,但我从未使用过这个模型,它几乎是空的


老实说,我一直在考虑转移到Symfony2和学说,而完全抛弃现行记录。我知道它不能解决这个问题,但我可能会放弃它,暂时保留我当前的解决方案。

要阅读文章,您可以在您的用户模型上定义多个关系,如下所述:

我认为您不需要代理模型UserReadArticles,只需要正确定义关系

要获取未读的文章,我在考虑Yii方法时也遇到了问题,但是比使用子选择查询更有效的方法是对用户\u read\u文章进行左连接,并检查来自用户\u read\u articles的列是否为空(没有匹配行),类似这样:

$this->getDbCriteria()->mergeWith( array(
    'alias' => 'articles',
    'join' => 'LEFT JOIN user_read_articles ON articles.id=user_read_articles.article_id',
    'condition' => 'user_read_articles.article_id IS NULL',
) );

您是否定义了从Articles到UserReadArticles的关系?如果是这样,我很确定您可以在命名范围的某个位置包含关系名称。我可以创建UserReadArticles,但我不确定如何将其放入命名范围。如果有帮助,请显示添加的关系定义。顺便说一句,这一问题在第二条原则下会更容易解决吗,还是会有一点不同?