我如何使用这种间接关系?

时间:2012-05-04 23:48:47

标签: orm relationship cakephp-2.1

我正在努力将声誉系统纳入我的网站,类似于SO。以下是它的结构:

用户拥有多个项目
用户有多个答案
项目有很多评级 答案有多个评分
评级属于Project.parent_type =项目
的项目 评级属于答案,其中Rating.parent_type =答案

评级的价值字段将是1到5之间的数字。用户每5星评价应获得+10,每个四星评价获得+5,每个三星评价获得+1。我目前设置它的方式是:在UsersController中的recalcRep($ id)操作(以及必要时在其他控制器中的其他操作)调用User模型中的calcRep($ id)方法,该方法应该是计算ID为$ id的用户的声誉。

public function calcRep($id) {
        $rep = 0;

        $data = $this->Rating->find('all'); //does not work, because it is not directly associated
        foreach($data as $rating) {
            if(($rating['Rating']['parent_type'] == 'Project' && $rating['Project']['user_id']==$id) or ($rating['Rating']['parent_type'] == 'Answer' && $rating['Answer']['user_id']==$id)) {
                if($rating['Rating']['value']==5) {
                    $rep += 10;
                } else if($rating['Rating']['value']==4) {
                    $rep += 5;
                } else if($rating['Rating']['value']==3) {
                    $rep += 2;
                }
            }
        }
        $data['User']['reputation'] = $rep;
        $this->save($data);
    }

我可能会以完全错误的方式接近这一点,但我无法弄清楚如何找到属于特定用户的任何子级的所有评级。

1 个答案:

答案 0 :(得分:0)

我认为cakePHP要求如果您要从控制器调用模型定义,控制器名称必须与模型相同,就像您调用$this->Rating一样,调用它的类需要RatingController或类似的东西。您最好的选择是调用find('all')内的RatingController并将其存储在您传递给calcRep()的临时变量中,即:

<?php
class RatingsController extends AppController {
    function calcRep($id) {
        $rep = 0;

        $data = $this->Rating->find('all'); //should work now, as you're calling it from the defined controller
        foreach($data as $rating) {
            if(($rating['Rating']['parent_type'] == 'Project' && $rating['Project']['user_id']==$id) or ($rating['Rating']['parent_type'] == 'Answer' && $rating['Answer']['user_id']==$id)) {
                if($rating['Rating']['value']==5) {
                    $rep += 10;
                } else if($rating['Rating']['value']==4) {
                    $rep += 5;
                } else if($rating['Rating']['value']==3) {
                    $rep += 2;
                }
            }
        }
        $data['User']['reputation'] = $rep;
        $this->save($data);
    }

}

?>

我相信还有一个loadModel()功能?也许如果你事先loadModel('Rating')它会起作用。

似乎CakePHP的PHP解释模型不允许你在模型中执行此操作,因为您尝试做的事情非常适合控制器。