写到 hasMany 与 Eloquent ORM/Laravel 的关系

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/21295850/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-14 08:54:18  来源:igfitidea点击:

Write to hasMany relationship with Eloquent ORM/Laravel

laravellaravel-4eloquent

提问by aleayr

Question about Laravel's Eloquent ORM. I've had a look on SO already, apologies if I've missed a similar question.

关于 Laravel 的 Eloquent ORM 的问题。我已经看过 SO 了,如果我错过了类似的问题,我深表歉意。

I have a User model, and I'm trying to write an array of Permissions back to the UserPermissions model, via the relationship in the User model.

我有一个 User 模型,我试图通过 User 模型中的关系将一组权限写回 UserPermissions 模型。

I've setup the hasMany link already, and can retrieve the correct data from the User object ($user->roles), but can't work out how to write back if it is at all possible.

我已经设置了 hasMany 链接,并且可以从用户对象 ( $user->roles) 中检索正确的数据,但是如果可能的话,我无法弄清楚如何回写。

This is my basic user model:

这是我的基本用户模型:

class User extends Eloquent {

    protected $table = 'users';

    public $timestamps = false;

    protected function roles() {

        return $this->hasMany('UserPermission');

    }

}

and the UserPermission model:

和 UserPermission 模型:

class UserPermission extends Eloquent {

    protected $table = 'users_permissions';

    public $timestamps = false;

    protected $fillable = ['role_id', 'user_id'];

}

At this stage, I've reverted to saving the User, and then running UserPermission::insert(), which allows an array to be passed, but I'd prefer to do it in one step if possible.

在这个阶段,我已经恢复到保存用户,然后运行UserPermission::insert(),这允许传递一个数组,但如果可能的话,我更愿意一步完成。

Anyone know if this is possible?

有谁知道这是否可能?

Thanks!

谢谢!



UPDATE:

更新

Table structure is below for your perusal:

表结构如下供您阅读:

users table

用户表

+------------------+------------------+------+-----+---------+----------------+
| Field            | Type             | Null | Key | Default | Extra          |
+------------------+------------------+------+-----+---------+----------------+
| id               | int(10) unsigned | NO   | PRI | 0       | auto_increment |
| username         | varchar(255)     | NO   |     |         |                |
+------------------+------------------+------+-----+---------+----------------+

users_roles table

users_roles 表

+------------------+------------------+------+-----+---------+----------------+
| Field            | Type             | Null | Key | Default | Extra          |
+------------------+------------------+------+-----+---------+----------------+
| id               | int(10) unsigned | NO   | PRI | 0       | auto_increment |
| name             | varchar(255)     | NO   |     |         |                |
| description      | varchar(255)     | YES  |     | NULL    |                |
| url_access       | varchar(255)     | NO   |     |         |                |
+------------------+------------------+------+-----+---------+----------------+

users_permissions table

users_permissions 表

+------------------+------------------+------+-----+---------+----------------+
| Field            | Type             | Null | Key | Default | Extra          |
+------------------+------------------+------+-----+---------+----------------+
| id               | int(10) unsigned | NO   | PRI | 0       | auto_increment |
| role_id          | int(10) unsigned | NO   |     |         |                |
| user_id          | int(10) unsigned | NO   |     |         |                |
+------------------+------------------+------+-----+---------+----------------+

role_idrelates to users_roles.idand user_idrelates to users.id

role_id涉及users_roles.iduser_id涉及users.id

As background logic, the users_rolestable has a url_accesscolumn which contains a url. If the user is assigned to that role, they have access to the subpages from that url.

作为后台逻辑,该users_roles表有一个url_access包含 url的列。如果用户被分配到那个角色,他们就可以从那个 url 访问子页面。

回答by Simo A.

I do not really see why you are using hasManyrelationship instead of belongsToMany. Actually it seems that your database structure is already such that is utilized by the belongsToMany relationship in Laravel.

我真的不明白您为什么使用hasMany关系而不是BeingsToMany。实际上,您的数据库结构似乎已经被 Laravel 中的belongsToMany 关系所利用。

My solution:

我的解决方案:

User.php

用户名.php

<?php

class User extends Eloquent {  

  public function roles() {
    return $this->belongsToMany('Role');
  }

  protected $table = 'users';
  protected $guarded = array('id', 'password');
}

Role.php

角色.php

<?php

class Role extends Eloquent {

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

protected $table = 'roles';
protected $guarded = array('id');

}

}

The corresponding database tables should be: users, rolesand role_user. These are according to Laravel's naming conventions in order to keelp things simple.

对应的数据库表应该是:users,rolesrole_user。这些是根据 Laravel 的命名约定,以保持简单。

Now you may call the syncmethod and pass an array to it:

现在您可以调用该sync方法并将数组传递给它:

$user->roles()->sync(array(1, 2, 3));

The sync method is briefly described in the Eloquent ORM documentation.

Eloquent ORM 文档中简要描述了同步方法。

回答by patrick

Okay here is what you could try.

好的,这是你可以尝试的。

Define a many to many relationship in bothof the models.

两个模型中定义多对多关系。

class UserPermission extends Eloquent {

protected $table = 'users_permissions';

public $timestamps = false;

protected $fillable = ['role_id', 'user_id'];

protected function users() {

    return $this->belongsToMany('User');

    }

}

Then, if you create a user, use laravel attach method to connect a user to a users_permission like so:

然后,如果您创建一个用户,请使用 laravel attach 方法将用户连接到 users_permission,如下所示:

$user = User::find(1);

$user->roles()->attach(1);

Attaching the role with an ID of 1 to the user with an ID of 1.

将 ID 为 1 的角色附加到 ID 为 1 的用户。

This is how you will be able to either attach a role to a user or attach a user to a role if you are creating a user or updating one.

如果您正在创建用户或更新用户,您可以通过这种方式将角色附加到用户或将用户附加到角色。

I really hope that this is of help to you. If not, feel free to ask me further. I have defined many to many relations just a few days ago with photos and tags so I am quite into it I would say.

我真的希望这对你有帮助。如果没有,请随时进一步问我。几天前我用照片和标签定义了多对多的关系,所以我会说我很喜欢。

Also, the laravel docs even have an example with users and roles:

此外,laravel 文档甚至有一个包含用户和角色的示例:

http://laravel.com/docs/eloquent#many-to-many

http://laravel.com/docs/eloquent#many-to-many

回答by Erik Aybar

From reading your question it "sounds like" you are asking the same question I ran into the other day.

通过阅读您的问题,“听起来”您在问我前几天遇到的相同问题。

I hope this helps enable to you "bulk update" the relationships while maintaining timestamps and avoiding duplicate relationships.

我希望这有助于您在维护时间戳和避免重复关系的同时“批量更新”关系。

Maybe there is a better way. I'm sure of it. But this worked perfectly for what I was trying to accomplish.

也许有更好的方法。我敢肯定。但这对我想要完成的工作非常有效。

*Warning: this is not tested code. In fact the exact solution I used myself with some search/replace to help relate to your question

*警告:这不是经过测试的代码。事实上,我自己使用的确切解决方案进行了一些搜索/替换,以帮助解决您的问题

Class User extends BaseModel {

    // [...]


    public function roles() {
        return $this->belongsToMany('Role');
    }



    public function addUserRoles(Array $add_user_role_ids) {
        /**
         * Prevent Duplicate Relationships
         */
        $existing_user_role_ids = $this->roles()->lists('user_role_id');

        $add_user_role_ids      = array_diff($add_user_role_ids, $existing_user_role_ids);
        if ($add_user_role_ids == null) return false;

        $add_user_role_ids      = UserRole::whereIn('id', $add_user_role_ids)->lists('id');
        if ($add_user_role_ids == null) return false;

        /**
         * Attach (Insert into Pivot Table)
         */
        if ( count($add_user_role_ids) > 0 ) {
            $this->UserRoles()->attach($add_user_role_ids);
            // Update timestamp
            $this->touch();
        }
        // Return successfully added user role ids Array
        return $add_user_role_ids;
    }



    public function removeUserRoles(Array $user_role_ids)
    {
        $this->touch();
        $this->roles()->detach($user_role_ids);
    }

    // [...]
}

Eloquent Docs

雄辩的文档

Find me on Twitter: @ErikOnTheWeb

在 Twitter 上找到我:@ErikOnTheWeb