LoginSignup
0
0

More than 5 years have passed since last update.

【CakePHP2】レビューの評価平均順にhogeを表示する

Last updated at Posted at 2017-05-31

はじめに

環境はCakePHP2.5.6

hogeに対して複数のreviewを持つ可能性があるという構成
Hoge hasMany Review

reviewsテーブルはid,score,content(レビュー内容),hoge_idという定義。

hogeをレビュー評価(平均)順にするには、どうしたらいいか……?

というものです。

解決策

「DBに新カラム?やめといて」と言われてしまいました。
正直それが一番いけそうだと思ったのですが……。ぐぇぇ

「VirtualFieldで出来るんじゃない?」なんていう助言も頂いたのですが、どうにも分かりませんでした。

最終的に辿り着いたのは、

① SQL文で綺麗にソートしたものを取得する
② 'order'にidを文字列で渡して、その順番で表示してもらう

という方法です。

調べまくっていて他にやっている人を見かけなかったので、ここに報告させて頂きます。

SQL文を好きなだけ使える上に、好き放題paginateも使えるんじゃないかと思います。

CakePHPの新たな可能性を見た、という気持ちです。

ソースコード

Model

Model/Hoge.php
public function getHogeSortScore() {
        $query = "
                SELECT
                                hoges.id,
                                hoges.name,
                                (sum(reviews.score))/count(review.id) as review_ave,
                                count(review.id) as review_count
                        FROM
                                hoges
                                        LEFT JOIN reviews
                                                ON (hoges.id = reviews.hoge_id)
                        group by hoges.id
                        order by review_ave desc, id;
        ";
        $data = $this->query($query);
        return $data
}

Controller

Controller/HogeController.php
public function index() {

        $score_sort_hoges = $this->Hoge->getHogeSortScore();

        $hoge_ids = array();
        foreach ($score_sort_hoges as $item) {
                // ただidだけの配列を作る
                $hoge_ids[] = $item['hoges']['id'];
        }
        // 配列に入ったものを,で区切った文字列に
        $str_hoge_ids = implode(',' , $hoge_ids);

        // 指定した順番に表示してもらうため
        $sort_order = 'FIELD(Hoge.id, ' . $str_hoge_ids . ')';

        $this->paginate = array(
                // 'conditions' => $conditions,
                'limit' => 10,
                'order' => $sort_order,
        );

        $options = array(
                'Hoge.del_flg' => 0,
        );
        $hoges = $this->paginate($options);
        $this->set(compact('hoges'));
}

修正

order byで、idも指定しておかないと
「1ページ目で出たものが2ページ目でも出てくる」なんていうヤバい表示になっていました。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0