我正在尝试构建一个“facebook 群组”风格的应用程序,其中包含充满成员的群组,每个成员都有一个成员类型(例如管理员、官员、用户……),每个群组都有其群组类型(公共(public)、关闭, secret )。
所以我创建了几个表:
users - (id, name ..)
groups - (id, name, group_type_id ..)
group_types - (id, type)
group_members - (user_id, group_id, membership_type_id)
group_membership_types - (id, type)
我相信这是构建数据库的正确方法(如果我错了请纠正我)。
现在我需要将它转换为 Eloquent 模型,所以我创建了模型,但在尝试建立它们之间的关系时真的很困惑,我读到“pivot”和“hasManyThrough”并且变得更加困惑。
这些是我到目前为止创建的模型:
class Group extends BaseModel
{
protected $table = 'groups';
public function Members() {
return $this->belongsToMany('App\GroupMemeber');
}
public function Type() {
return $this->belongsTo('App\GroupType');
}
}
--
class GroupType extends BaseModel
{
protected $table = 'group_types';
protected $guarded = ['id', 'type'];
}
--
class GroupMemebershipType extends BaseModel
{
protected $table = 'group_membership_types';
}
--
class GroupMember extends BaseModel
{
protected $table = 'group_members';
public function User() {
return $this->belongsTo('App\User');
}
public function Group() {
return $this->hasMany('App\Group');
}
public function MembershipType() {
return $this->belongsTo('App\GroupMemebershipType');
}
}
我做的对吗?你将如何创建这些模型?
最佳答案
数据透视表约定
按照惯例,数据透视表命名为 tablename1_tablename2
,其中 tablename1
按字母顺序取代 tablename2
。在这种情况下,group_members
应该是 group_user
。如果更改此设置,则无需定义 $table 变量,因此您可以根据需要删除这些变量以清理代码。
Eloquent 关系
Eloquent 关系是well documented ,如果您不确定,可以随时引用代码文档,它非常简单:
有一个
Define a one-to-one relationship.
有很多
Define a one-to-many relationship.
有许多通过
Define a has-many-through relationship.
属于
Define an inverse one-to-one or many relationship.
belongsToMany
Define a many-to-many relationship.
使用数据透视表时,您可以添加 ->withPivot()
,Eloquent 会自动找到您的常规命名数据透视表。您甚至不需要这些“中间”对象的模型,因为它们(可能)不会在您的表示层中使用。
三向数据透视表
现在,关于您的组成员资格,事情会变得有点复杂。 hasManyThrough
关系用于 accessing distant relations via an intermediate relation , 而不是您要查找的内容。 Laravel 不为这种类型的关系提供任何“即插即用”功能,虽然有 is a Laravel 4 library为此,它不是很动态,但只提供三向功能。现在这很好,但是如果您决定在将来扩展您的数据透视表怎么办?然后这将中断。
重构数据库
通过避免使用三向数据透视表,您的代码(和表结构)更易于维护且更具可读性。我认为这适用于任何具有三向关系的数据透视表,一个好的经验法则是通过使用更智能的表结构来避免它。
结果
用户
一个用户
- 属于许多成员(member)
- 通过成员(member)资格拥有许多群组
代码:
class User extends Model
{
public function memberships() {
return $this->belongsToMany('App\Membership');
}
public function groups() {
return $this->hasManyThrough('App\Group', 'App\Membership');
}
}
成员(member)资格
成员(member)资格
- 有很多用户
- 属于一个团体
代码:
class Membership extends Model
{
public function users() {
return $this->hasMany('App\User');
}
public function group() {
return $this->hasOne('App\Group');
}
}
组
一组
- 有很多成员(member)
- 通过成员(member)制拥有很多用户
代码:
class Group extends Model
{
public function memberships() {
return $this->hasMany('App\Membership');
}
public function users() {
return $this->hasManyThrough('App\User', 'App\Membership');
}
}
关于php - 需要帮助构建 Eloquent 多对多关系(laravel 5.1),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32562823/