
前回、LEFT JOINまではやったのですが、
今度はその下の孫のデータを取ることをしてみます。
孫の階層をJOINして取り出す場合
親から見て、孫のテーブルを結合して取り出す場合です。
モデルに下記のように記述します。
public $recursive = 階層数;
(例)
Postモデルで処理する場合
| モデル名 | Postモデル | → | UserPostモデル | → | Commentモデル |
|---|---|---|---|---|---|
| テーブル名 | posts | → | user_posts | → | cooments |
| 関連するフィールド名 | id | → | post_id | ||
| 関連するフィールド名 | /td> | id | → | user_post_id |
Postモデル
<?php
class Post extends AppModel{
public $hasOne = 'UserPost'; //結合モデル
public $recursive = 2; //PostモデルからみてCommentモデルの階層
}
?>
UserPostモデル
<?php
class UserPost extends AppModel{
public $hasOne = 'Comment'; //結合モデル
}
?>
以上です。
ただ、モデルで記述すると常に下の階層まで結合されて
SQLが多くなって表示時間が遅くなりました。
なので、コントローラーでも指定できるので
使いたいときだけコントローラーでの指定もありだと思います。
コントローラーで孫の階層をJOINして取り出す場合
(例)
Postモデルで処理する場合
| モデル名 | Postモデル | → | UserPostモデル | → | Commentモデル |
|---|---|---|---|---|---|
| テーブル名 | posts | → | user_posts | → | cooments |
| 関連するフィールド名 | id | → | post_id | ||
| 関連するフィールド名 | id | → | user_post_id |
Postモデル
<?php
class Post extends AppModel{
public $hasOne = 'UserPost'; //結合モデル
}
?>
UserPostモデル
<?php
class UserPost extends AppModel{
public $hasOne = 'Comment'; //結合モデル
}
?>
Postsコントローラー
使いたいところ(例えば function edit()内)に
$this->Post->recursive = 2;
と書けばいいみたいです。
これなら、使いたいときだけ孫の階層が使えるみたいです。
階層の考え方
recursiveじゃ階層で考えるみたいなんですが、
hasOne,belongsToとhasManyで少し違いがあるようです。
| recursive | -1 | 0 | 1 | 2 | 3 |
|---|---|---|---|---|---|
| hasOne,belongdTo | カレントのみ | 第1次アソシエーションテーブル | 第1次アソシエーションテーブル | 第2次アソシエーションテーブル | 第3次アソシエーションテーブル |
| hasMany | カレントのみ | – | 第1次アソシエーションテーブル | 第2次アソシエーションテーブル | 第3次アソシエーションテーブル |
最初の0か1で少し違いが出るようです。
詳細はこちらに図があるのでわかりやすいと思います。
recursiveの正しい理解CakePHP
階層の考え方が微妙に難しいです。
慣れるまでは大変ですね。
でも、簡単にJOINしてくれるのは助かります。
