Laravel define belongsToMany relation ships without providing second parameter - laravel

In laravel i try to make a simple relation-ship between two table as users and wallets without providing second parameter, but when i try to access between them i get error:
Base table or view not found: 1146 Table 'sample.user_wallets' doesn't exist
//user
Schema::create('users', function (Blueprint $table) {
$table->bigIncrements('id');
$table->unsignedBigInteger('parent_id')->nullable();
//...
$table->softDeletes();
$table->timestamp('created_at')->useCurrent();
$table->timestamp('updated_at')->useCurrent();
});
//wallets
Schema::create('wallets', function (Blueprint $table) {
$table->bigIncrements('id');
$table->string('wallet_name');
$table->string('wallet_number');
$table->timestamps();
});
//user_wallet
Schema::create('user_wallet', function (Blueprint $table) {
$table->foreignId('user_id')->constrained()->cascadeOnDelete();
$table->foreignId('wallet_id')->constrained()->cascadeOnDelete();
$table->primary(['user_id','wallet_id']);
});
User model:
public function wallet(): BelongsToMany
{
return $this->belongsToMany(UserWallet::class);
}
Wallet model:
public function user(): BelongsToMany
{
return $this->belongsToMany(User::class);
}
and by this below code i try to access user's wallets:
$this->user_wallets = auth()->user()->with('wallet')->get();

IN Your User Model:
change
public function wallet(): BelongsToMany
{
return $this->belongsToMany(UserWallet::class);
}
To : THis
public function wallets(): BelongsToMany
{
return $this->belongsToMany(Wallet::class,'user_wallet');
}
In Your Wallet Model:
public function users(): BelongsToMany ///not user
{
return $this->belongsToMany(User::class);
}
Note: U dont need UserWallet Model Since it is belongsTOMany Relationship
Suggestion: In real life example a user have many wallet and a wallet is only belongs to one user so the relation is HasMany(on to Many)

It should be plural. wallets and users
User Model:
public function wallets(): BelongsToMany //not wallet
{
return $this->belongsToMany(Wallet::class);
}
Wallet model:
public function users(): BelongsToMany //not user
{
return $this->belongsToMany(User::class);
}

Related

Laravel creates a one-to-many relationship instead of one-to-one

When I create a one-to-one relationship migration, laravel creates a one-to-many relationship. I tried to solve this in different ways and nothing worked.
How can I solve this?
Company:
class Company extends Model
{
public function user()
{
return $this->hasOne(User::class);
}
...
}
User:
class User extends Authenticatable
{
public function company(){
return $this->belongsTo(Company::class);
}
...
}
Migrations:
Schema::create('Company', function (Blueprint $table) {
$table->mediumIncrements('idCompany');
...
});
Schema::create('User', function (Blueprint $table) {
$table->id();
$table->increments('idUser');
$table->unsignedMediumInteger('Company_idCompany')
->unique()
->nullable();
$table->foreign('Company_idCompany')
->references('idCompany')
->on('company')
->onDelete('set null');
...
});
Laravel is creating nothing (on the migration), you always have to manually create the Model relationship (you are using hasOne and belongsTo, so that is 1-to-1) and migrations (you are creating User and Company not following the standards).
So, update your migrations to:
Schema::create('company', function (Blueprint $table) {
$table->id();
...
});
Schema::create('user', function (Blueprint $table) {
$table->id();
$table->increments('user_id');
$table->foreignId('company_id')
->unique()
->nullable();
$table->foreign('company_id')
->references('id')
->on('company')
->onDelete('set null');
...
});
See that I have moved everything to lowercase and snake case, remember to follow Laravel conventions or you are going to have a harder time working with Models...
Then, your relationships are correct:
class Company extends Model
{
public function user()
{
return $this->hasOne(User::class);
}
...
}
class User extends Authenticatable
{
public function company(){
return $this->belongsTo(Company::class);
}
...
}
So, when you do access a relationship, it will work out of the box now.
If you do Company::first()->user, that will return User or null, and if you do User::first()->company, that will return Company or null, there is no 1-to-N.

Can't create one to many relationship on same model

I want to create sponsors users on my website. I use the same model as relationship.
User.php (model):
public function sponsor(): HasMany
{
return $this->hasMany(self::class, 'sponsored_id', 'sponsor_id');
}
public function sponsored(): BelongsTo
{
return $this->BelongsTo(self::class, 'sponsor_id', 'sponsored_id');
}
Sponsor rows :
Schema::table('users', function (Blueprint $table) {
$table->foreignId('sponsor_id')->nullable();
$table->foreignId('sponsored_id')->nullable();
});
My UserSeeder:
$sponsor = User::factory()->create(['name' => 'sponsor']);
$sponsor->sponsor()->save(
User::factory()->make()
);
As per your comment you are trying to retrieve one record from sponser so it should be
$sponsor->sponsor()->first()

laravel eloquent relation one to one

I have a Laravel migration like this
usergroups:
Schema::create('usergroups', function (Blueprint $table) {
$table->integer('id')->primary();
$table->string('name');
$table->string('slug');
});
users:
Schema::create('users', function (Blueprint $table) {
$table->integer('nik')->primary();
$table->string('name');
$table->string('username');
$table->string('password');
$table->string('telp', 15);
$table->integer('usergroup_id');
$table->rememberToken();
$table->timestamps();
});
Schema::table('users', function ($table) {
$table->foreign('usergroup_id')->references('id')->on('usergroups')->onDelete('cascade');
});
User model
public function group()
{
return $this->belongsTo(Usergroup::class, 'id');
}
Usergroup model
public function user()
{
return $this->hasMany(User::class, 'usergroup_id');
}
I get blank data with this
$petugas = User::find(1);
return $petugas->group;
anyone help me, please...
This is not a One to One relationship i.e (user has one phone and one phone belongs to one user)
A group has many users in this case, One to Many relationship
You're migrating the users table twice, move the foreign key to the migration
Schema::create('users', function (Blueprint $table) {
$table->integer('nik')->primary();
$table->string('name');
$table->string('username');
$table->string('password');
$table->string('telp',15);
$table->integer('usergroup_id');
$table->foreign('usergroup_id')->references('id')->on('usergroups')->onDelete('cascade');
$table->rememberToken();
$table->timestamps();
});
Hope this helps
First of all, this is not a One to One relationship. This is a One to Many relationship. The relation you have build in wrong way according to migration files.
The relation code block should look like this.
public function group()
{
return $this->hasMany(Usergroup::class);
}
public function users()
{
return $this->belongsTo(User::class);
}
Some more info:
In your scenario there might be two possible fact.
A user has many groups, but a group is belongs to only one
user.
A group has many users but a user is belongs to only one
group.
Fact 1: In this case the foreign key column should place in groups table. To follow the convention make the foreign column name user_id in groups table. And the code should look like this
public function groups()
{
return $this->belongsTo(Usergroup::class);
}
public function user()
{
return $this->hasMany(User::class);
}
Fact 2: In this case the foreign key column should place in users table. To follow the convention make the make the foreign column name group_id in users table And the relation code should look like this
public function group()
{
return $this->hasMany(Usergroup::class);
}
public function users()
{
return $this->belongsTo(User::class);
}
i got it...
this on user model
public function group()
{
return $this->belongsTo(Usergroup::class,'usergroup_id');
}
and this on usergroup model
public function user()
{
return $this->hasMany(User::class,'usergroup_id');
}

RelationShip Eloquent hasOne

I do not understand how the relationShips are working with Eloquent. Imagine an user with one role. I wrote this in my model User :
public function role()
{
return $this->hasOne('App\Models\Role');
}
And this in my model Role :
public function user()
{
return $this->belongsTo('App\User');
}
After that i would like to retrieve the role of the user connected , like that :
Auth::user()->role->role_name
But it throw an exception :
Undefined column: 7 ERROR: column roles.user_id does not exist
Does it not work like that?
You're missing the user_id foreign column in the roles table, Eloquent assumes that column to exist in order to link a User with a Role
Schema::create('roles', function (Blueprint $table) {
$table->bigIncrements('id');
$table->string('role_name');
$table->unsignedBigInteger('user_id');
$table->foreign('user_id')->references('id')->on('users')->onDelete('cascade');
$table->timestamps();
});
Update: given a hasOne relationship
App\User model
public function role()
{
return $this->hasOne('App\Models\Role');
}
App\Model\Role model
public function user()
{
return $this->belongsTo('App\User');
}
DatabaseSeeder
$user = factory('App\User')->create();
$user->role()->create([
'role_name' => 'Admin'
]);
routes/web
use Illuminate\Support\Facades\Auth;
Route::get('/', function () {
return Auth::user()->role->role_name;
});
Results => Admin
You should use the belongsTo() relationship in your User model for the role relationship :
public function role()
{
return $this->belongsTo('App\Models\Role');
}

Fetching Relationship Model Data

I have the Below Table Structure
Users table
id- integer
name-string
Casefiles table
id- integer
user_id- foreign_key
name-string
Followups table
id- integer
date- date
casefile_id-foreign_key
I'm using the below Relationship between this models
User.php
public function casefiles()
{
if ($this->hasRole(['sales_executive'])) {
return Casefile::where('user_id', $this->id);
}
}
Casefile.php
public function user()
{
return $this->belongsTo('App\User');
}
public function followups()
{
return $this->hasMany('App\FollowUp');
}
Followup.php
public function casefile()
{
return $this->belongsTo('App\Casefile');
}
I want to fetch Users followups directly. How can i achive this ?
you need to use hasManyThrough() in your User.php you can add this,
public function followUps()
{
return $this->hasManyThrough('App\FollowUp','App\Casefile');
}
then you can normally call the followups using User::with('followUps')->find(1)->followUps
I have noticed that you are checking role in your relationship $this->hasRole(['sales_executive'] this may occur error as you are not if the statement is false. I think you take another approached and handle that as well. for more information on hasManyThrough prefer this link
This should be the case for a HasManyThrough Relationship.
In your case it should be
// Followups migration
Schema::create('followups', function (Blueprint $table) {
$table->bigIncrements('id');
$table->date('date');
$table->unsignedBigInteger('casefile_id')->nullable();
$table->timestamps();
$table->foreign('casefile_id')
->references('id')
->on('casefiles');
});
// Casefile migration
Schema::create('casefiles', function (Blueprint $table) {
$table->bigIncrements('id');
$table->string('name');
$table->unsignedBigInteger('user_id')->nullable();
$table->timestamps();
$table->foreign('user_id')
->references('id')
->on('users');
});
// User.php
public function followups() {
return $this->hasManyThrough(FollowUp::class, Casefile::class);
}
// YourController.php
$user = User::all()->first();
dd($user->followups);

Resources