Back

Relationships (One-to-One)


square360-steven posted 5 years ago

I'm new to Laravel put like what I see so far. Here's my issue. In my example app I have 2 models User and UserProfile. They are a one-to-one relationship. I am able to add a UserProfile using the following:

$user = User::find(10); $profile = new UserProfile(); $profile->name = 'Steven'; $user->UserProfile()->save($profile);

The problem lies in how do I update the UserProfile -> name?

I thought something like this could work

$user->UserProfile()->name = 'Steven'; $user->save();

But I get errors, so that is clearly wrong.

Can anyone shed some light and help me out.

Thank you

  • Steven
usm4n replied 5 years ago

In your user model define a relation like

class User extends Eloquent {

    public function profile()
    {
        return $this->hasOne('Profile'); //Profile is your profile model
    }

}

now you can access profile like :

$profile = $user->profile();
$profile->whatever = 'anything';
square360-steven replied 5 years ago

@usm4n, I've added that function to my model and do the following

$user = User::find(10); $profile = $user->UserProfile(); $profile->name = 'Steven'; $profile->save();

The error returned is:

ErrorException Argument 1 passed to Illuminate\Database\Eloquent\Relations\HasOneOrMany::save() must be an instance of Illuminate\Database\Eloquent\Model, none given

All I want to do is if there is no profile record for user_id (10), create one. If there is a profile record for the user, update it. Also note, there can only be 1 record in the profile table for each user. I have a unique key on the user_id column.

Thanks

usm4n replied 5 years ago

try this:

$user = User::find(10);
$profile = $user->profile();
$profile->name = 'Steven';
$user->profile()->save($profile);

hope this helps... please read the documentation for further details.

zenry replied 5 years ago
$profile = $user->profile();

should be

$profile = $user->profile; // note the removal of ()

or

$profile = $user->profile()->first();

source http://laravel.com/docs/eloquent#dynamic-properties

square360-steven replied 5 years ago

@usm4n, I've read the docs, but it doesn't seem to answer the questions I ask. I tried your method, got an error still

@zenry, I removed the () and got the following error

ErrorException Creating default object from empty value

My Code: $user = User::find(10); $profile = $user->UserProfile; $profile->name = 'Steven';

$user->UserProfile()->save($profile);

zenry replied 5 years ago

look at this post http://laravel.io/forum/02-19-2014-relationships-one-to-one?page=1#reply-1691

you need to have a method in your User class with the name 'UserProfile' id you are going to use your code $user->UserProfile;

'$user->UserProfile;'

User::UserProfile()---^

square360-steven replied 5 years ago

@zenry, here are my models

User.php

<?php use Illuminate\Auth\UserInterface; use Illuminate\Auth\Reminders\RemindableInterface; class User extends Eloquent implements UserInterface, RemindableInterface { public $timestamps = true; public function UserProfile() { return $this->hasOne('UserProfile'); } } UserProfile.php <?php class UserProfile extends Eloquent { public $table = 'user_profiles'; public $timestamps = false; public function user() { return $this->belongsTo('User'); } } From the looks of everything, it's correct, but I'm still getting errors. Worth noting, if a record in the user_profiles table exists with the user_id of 10 it will update fine with the above code.
alainbelez replied 5 years ago Solution

maybe you need to initialize it before using it.

$user = User::find(10);
$profile = $user->UserProfile ?: new UserProfile;
$profile->name = 'Steven';
$user->UserProfile()->save($profile);
usm4n replied 5 years ago

Try to go like this:

  1. create a table with name 'users'
  2. create a table with name 'profiles'
  3. create a user model named as 'User' :
class User extends Eloquent implements UserInterface, RemindableInterface {

public function profile() {
    return $this->hasOne('Profile');
}
...
}
  1. create profile model named as 'Profile':
class Profile extends Eloquent {

public function user() {
    return $this->belongsTo('User');
}
}
  1. and in your controller use:
$user = User::find(10);
$profile = $user->profile;   // as zenry pointed out the typo.
$profile->name = 'Steven';
$user->profile()->save($profile);

may this helps :(

square360-steven replied 5 years ago

Thanks everyone for the help. I really appreciate it. Turns out @alainbelez answer was the solution I needed.


Sign in to participate in this thread!



We'd like to thank these amazing companies for supporting us