HABTM の仕組みを理解していないと思います。本のこの部分を読んでください。関係を機能させるには、テーブルに加えて friends_users テーブルが必要です。このように設定する場合は、フレンドシップを多くのユーザーを持ち、所属するものとして定義する必要があると思います。
ただし、現在のセットアップで HABTM 関係が必要かどうかは疑問です。ユーザーには多くの友達がいるようです。それだけです。その関係の使用を検討すると、期待どおりに関連する ID が得られます。フレンドの属しているユーザーを定義することを忘れないでください。
これが私の正規の Cake 2.0 Friendship チュートリアルです。CakePHP 2.1 をダウンロードしたので、新たなスタートを切ることができました。最初にセキュリティ ソルトと暗号を変更し、次にデータベース接続を追加しました。次に、データベースを次のように構成しました。
データベース:
users
テーブル:
id | int(11)
created | datetime
username | varchar(255)
friendships
テーブル:
id | int(11)
user_from | varchar(255)
user_to | varchar(255)
created | datetime
status | varchar(50)
明らかに、users テーブルにはさらに多くのものを含めることができますが、これは私が必要とする最小限のものです。
モデル:
さて、これはトリッキーな部分です。User モデルで定義した関係を次に示します。
class User extends AppModel {
/* Other code if you have it */
var $hasMany = array(
'FriendFrom'=>array(
'className'=>'Friendship',
'foreignKey'=>'user_from'
),
'FriendTo'=>array(
'className'=>'Friendship',
'foreignKey'=>'user_to'
)
);
var $hasAndBelongsToMany = array(
'UserFriendship' => array(
'className' => 'User',
'joinTable' => 'friendships',
'foreignKey' => 'user_from',
'associationForeignKey' => 'user_to'
)
);
/* Again, other code */
}
これが私の友情モデルです:
class Friendship extends AppModel {
/* Other code if you have it */
var $belongsTo = array(
'UserFrom'=>array(
'className'=>'User',
'foreignKey'=>'user_from'
),
'UserTo'=>array(
'className'=>'User',
'foreignKey'=>'user_to'
)
);
/* Again, other code */
}
モデルに関する注意: フレンドシップ モデルは 2 人のユーザーに属します。ユーザー モデルには 3 つの関連付けがあります。User Model の 2 つの hasMany リレーションシップはどちらも Friendship モデルのデータにアクセスするためのエイリアスであるため、コントローラから$this->User->FriendTo
またはを使用して Friendship モデルにアクセスできます。$this->User->FriendFrom
私は最初、Friendship モデルのセットアップを反映して、これらの UserFrom と UserTo を呼び出しましたが、Cake は類似点についてひっかかったので、それらをより明確にする必要がありました。
コントローラーとビュー: ベイク ユーティリティを使用して、コントローラーとビューをベイクしました。次に、2 人のユーザー (Daniel と Martin) を作成し、Daniel から Martin への新しいフレンドシップを作成しました。ステータスはrequested
です。その後、友好度を に更新しましたconfirmed
。
次のビューレス カスタム ユーザー アクションを作成して、UsersController からの友情に関するデータ取得を示します。
public function test() {
$data = $this->User->FriendFrom->find('all',
array(
'conditions'=>array('user_from'=>1),
'contain'=>array('UserTo')
)
);
die(debug($data));
}
この検索では、UserModel の hasMany 関係を使用して Friendship モデルにアクセスし、ID が 1 のユーザーが関係を開始した関係の関連データをuser_from
取得します。user_to
あなたの特定の発見:
マーティン、あなたが探している発見は、このシステムでは非常にシンプルです。別の方法で行うこともできますが、関係に常に2つの側面がある限り、常に同様の方法を使用することになります. あなたがしなければならないのは、あなたのユーザーIDがuser1またはuser2のいずれかである関係のリストを取得することです(私の場合、関係を開始した人を知るために、それらをuser_toおよびuser_fromとして保存しています-これがあなたを怖がらせたものだと思います)。次に、配列全体を繰り返し処理し、その特定の配列で私が user1 か 2 かに基づいて、関連するフレンド データを選択します。これは非常に単純な方法で、ユーザー モデルに入れるだけです。ダイを変更します(debug()); コントローラーからreturn $friendslist
呼び出して配列を取得できるようにします。
public function getFriends($idToFind) {
$data = $this->FriendFrom->find('all',
array(
'conditions'=>array(
'OR'=> array(
array('user_to'=> $idToFind),
array('user_from'=> $idToFind)
)
)
)
);
$friendslist = array();
foreach ($data as $i) {
if ($i['FriendFrom']['user_from'] == $idToFind){
$friendslist[] = $i['UserTo'];
}
elseif ($i['FriendFrom']['user_to'] == $idToFind){
$friendslist[] = $i['UserFrom'];
}
}
die(debug($friendslist));
}