33

I have three tables,

roles(id, name);
users(id, email, password);
user_role(id, user_id, role_id);

In this scenario, I have users table is associated to roles table with many to many relation.

I have two eloquent model as

Role
+users(){
    belongsToMany('User')
}

User
+roles(){
    belongsToMany('Role')
}

Now, the question is when I want to add a new user along with ids of roles that I would like to assign to users. How can I insert values to pivot table with Laravel best practices?

My existing code is:-

$roles = Input::get('roles'); // arrays of role ids

$user = new User();
$user->username = Input::get('username');
$user->password = Hash::make(Input::get('password'));
$user->save();

What to do next???

Tiago Martins Peres
  • 14,289
  • 18
  • 86
  • 145
Dipendra Gurung
  • 5,720
  • 11
  • 39
  • 62

2 Answers2

40

It's really all described in the documentation.

Anyway, here's how you do it:

$user = new User();
$user->username = Input::get('username');
$user->password = Hash::make(Input::get('password'));
$user->save();
$user->roles()->attach($roles);

The important part is that you have to save the user before attaching (using attach()) the roles because otherwise the user doesn't have an id yet to be used in the pivot table.

Tiago Martins Peres
  • 14,289
  • 18
  • 86
  • 145
lukasgeiter
  • 147,337
  • 26
  • 332
  • 270
  • I tried it, but it is returning an error, Call to undefined method Illuminate\\Database\\Eloquent\\Collection::attach() – Dipendra Gurung Feb 02 '15 at 10:04
  • 6
    Just to clarify, the parentheses matter! ```$user->roles()``` NOT ```$user->roles``` – dloomb Nov 03 '15 at 01:04
  • @lukasgeiter it's not that clear. How are we to know the `attach()` needs to be done after the record has been saved? – tread Dec 13 '15 at 20:11
  • 1
    @surfer190 Well that's how all eloquent relations work. First you save one side, and then associate the other. But I agree that this might not be very clear from the documentation. – lukasgeiter Dec 13 '15 at 20:19
  • The same goes in laravel 5.4 also? – siddiq Apr 26 '17 at 13:15
  • Yes @siddiq same goes for 5.4 . Need to insert one record before trying to associate it with another since the association uses the primary key from the parent to insert into the child so if there hasn't been an insertion, then there will be no id. – FONGOH MARTIN Nov 01 '17 at 05:03
  • 1
    Another clarification, this only works with `belongsToMany` relationship and not `hasMany` – Tofandel May 06 '21 at 16:43
  • 1
    I am confused, what is the type of $roles variable is it an object or array please clarify that I also read the documentation but is a bit complicated for me? – MANSOOR KOCHY Jan 02 '22 at 06:42
  • 1
    Knowing what to look for in the documentation is half the battle for new people. – user2924019 Nov 29 '22 at 15:37
0

If there are timestamps like created_at and updated_at on the pivot table, you can pass those as another parameter to the attach method like below.

<?php

use Carbon\Carbon;

// Assuming $roles is an array, say like having values as [1,2,80,200] etc.

$user->save();
$user->roles()->attach($roles, array(
   'created_at' => Carbon::now(), // or date("Y-m-d H:i:s")
   'updated_at' => Carbon::now()
));
nice_dev
  • 17,053
  • 2
  • 21
  • 35