在Eloquent中查询透视属性

时间:2013-11-21 11:55:48

标签: php laravel-4 eloquent

我正在创建一个基本的消息传递系统,需要在数据透视表上查询数据。相关表格的设置如下:

|  conversations  |  messages         |  message_user  |  conversation_user  |
------------------------------------------------------------------------------
|  id             |  id               |  message_id    |  conversation_id    |           
|  created_at     |  conversation_id  |  user_id       |  user_id            |
|  updated_at     |  content          |  sender        |                     |
|  deleted_on     |  created_at       |  unread        |                     |
|                 |  updated_at       |  deleted       |                     |
------------------------------------------------------------------------------

简单地说,每个对话都有用户,每个用户都有消息,每个消息都在对话中。 message_user表是一个数据透视表,与conversaton_user表一样。

我的模型设置如下:

class Message extends Eloquent {
    public $touches = ['conversation'];

    public function conversation() {
        return $this->hasOne('Conversation');
    }

    public function user() {
        return $this->belongsToMany('User')->withPivot(['sender', 'unread', 'deleted']);
    }

    public function session() {
        return $this->hasOne('UserSession');
    }
}

class Conversation extends Eloquent {

    public function users() {
        return $this->belongsToMany('User');
    }

    public function product() {
        return $this->hasOne('Product');
    }

    public function messages() {
        return $this->hasMany('Message');
    }
}

class User extends Eloquent {

    ...

    public function conversations() {
        return $this->belongsToMany('Conversation');
    }

    public function messages() {
        return $this->belongsToMany('Message');
    }

    ...

}

当邮件被保存时,它会使用对话中涉及的每个用户的字段更新邮件用户:

foreach($conversation->users as $user) {
    $message->users()->attach($user->id [
        'sender' => (Auth::user()->id === $user->id),
        'unread' => (Auth::user()->id !== $user->id),
        'deleted' => false,
    ]);
}

要获取所有用户对话,请执行以下操作:

$user = Auth::user();
foreach($user->conversations as $conversation) {
    // get each message from the conversation
    foreach($conversation->messages as $message) {

    }
}

我的问题是,在决定是否向用户显示邮件之前,我需要查询数据透视表以查明用户是否已删除邮件,因为删除特定于每个用户。

我可以在对话模型中做这样的事情:

public function notDeletedMessage() {
    return $this->messages()
                ->join('message_user', 'message_user.message_id', '=', 'messages.id')
                ->where('message_user.user_id', Auth::user()->id)
                ->where('message_user.deleted', false);
}

但是看起来有点hacky,有没有更好的方法来实现这个功能?

1 个答案:

答案 0 :(得分:0)

您是否尝试过对集合使用pivot? http://four.laravel.com/docs/eloquent#working-with-pivot-tables