Laravel 8: Role ID Does Not Submitted Into One To Many Relationship

Viewed 174

I'm using Laravel 8 for my project, and in this project, I want to apply OneToMany relationship between users and roles tables.

So at the Models, I've added these:

Role.php:

public function users()
{
    return $this->hasMany(Role::class);
}

User.php:

public function role()
{
    return $this->belongsTo(User::class);
}

Then for creating new users, I've added this form field:

<div class="form-group">
   <label class="col-sm-2 control-label">Role</label>
   <select class="form-control" name="role" dir="ltr">
       @foreach(\App\Models\Role::all() as $role)
         <option value="{{ $role->id }}">{{ $role->name }}</option>
      @endforeach
   </select>
</div>

And at the Store method, I coded this:

public function store(Request $request)
{
    $validate_data = Validator::make(request()->all(),[
        'name' => 'required|min:4',
        'email' => 'required|email|unique:users',
        'status' => 'required',
        'role' => 'required',
        'password' => 'required|min:6'
    ])->validated();

    $creation = User::create([
        'name' => $validate_data['name'],
        'email' => $validate_data['email'],
        'status' => $validate_data['status'],
        'role_id' => $validate_data['role'],
        'password' => bcrypt($validate_data['password'])
    ]);

    if($creation){
        return redirect()->back();
    }else{
        return '1003';
    }
}

But now the problem is, whenever I try to add a new user, it will be added successfully to the table users but the column role_id will remain empty:

enter image description here

And when I say dd($request); it prints this:

enter image description here

As you can see it stores the role but I don't know why it does not save it in the database!

So what is going wrong here? How can I fix this issue?

I would really appreciate any idea or suggestion from you guys...

Thanks in advance.

2 Answers

Most likely you don't have role_id as a $fillable on your model.

class User {
    $fillable = [
        ...,
        'role_id',
    ];
}

Filling relationships as a property is not optimal, it can lead to relationships being null, even thou you just populated the data. The correct approach is to use associate() method call. This also provides the benefit of returning a 404 if role is not found, because you have to fetch the Role before associating() it. In most API's, this would be the standard if a relation is not present and just more sturdy code, to avoid foreign key errors from SQL.

$user = new User([
    'name' => $validate_data['name'],
    'email' => $validate_data['email'],
    'status' => $validate_data['status'],
    'password' => bcrypt($validate_data['password'])
]);

$user->associate(Role::findOrFail($validate_data['role']));
$user->save();

I had this mistake too previously, I believe this might be because you forgot to add role_id to the $fillable variable in User.php model.

Related