2015-08-15 2 views
0

Допустим, у вас есть пользователь и Friend SchemasLaravel & Eloquent - Отношения запроса «Друзья»

user: 
    - id 
    - username 

friends: 
    - id 
    - user_id 
    - friend_id 

А «дружба» определяется наличием двух взаимных записей. И позволяет говорить, что это всего лишь односторонние отношения, это ожидающий запрос. Таким образом, в таблице: друзей

user_id: 5 | friend_id: 6 
user_id: 6 | friend_id 5 

В модели пользователя, вы бы тогда:

public function friends() 
    { 
     return $this->belongsToMany(self::class,'friends','user_id','friend_id')->withTimestamps(); 
    } 

Однако, это не вся история, потому что это не проверить на присутствие взаимные отношения.

Как бы вы это определили? Должен ли метод friends() отвечать за дальнейший запрос данных? Или этот метод подходит, а в случаях, когда вы хотите получить взаимную дружбу, вы должны добавить область запроса? Например

$this->user->friends->mutual() 

ИЛИ

$this->user->friends->pending() 

ответ

0

Законченное выяснить это на основе this answer. Тем не менее, я изменил функциональность merge() на intersect(), потому что я не использую флаг approved, чтобы определить погоду, дружба взаимная. Я использую только наличие двух отношений.

Так что в моем случае. отношения являются:

public function myFriends() 
{ 
    return $this->belongsToMany(self::class,'friends','user_id','friend_id')->withTimestamps(); 
} 

public function friendsOf() 
{ 
    return $this->belongsToMany(self::class,'friends','friend_id','user_id')->withTimestamps(); 
} 

И другая логика:

public function getFriendsAttribute() 
{ 
    if (! array_key_exists('friends', $this->relations)) $this->loadFriends(); 

    return $this->getRelation('friends'); 
} 

protected function loadFriends() 
{ 
    if (! array_key_exists('friends', $this->relations)) $this->setRelation('friends', $this->mergeFriends()); 
} 

protected function mergeFriends() 
{ 
    return $this->myFriends->intersect($this->friendsOf); 
} 
Смежные вопросы