Relationship not working and looking for a strange table name? - laravel

I have created a migration for a lookup table with a many to many relationship.
Schema::create('user_partner__organization', function (Blueprint $table) {
$table->id();
$table->unsignedBigInteger('user_id');
$table->unsignedBigInteger('partner_organization_id');
$table->foreign('user_id')
->references('id')
->on('users');
$table->foreign('partner_organization_id')
->references('id')
->on('partner_organizations');
});
}
Then I am setting up the relationships to be able to go through the user_partner__organization table
In UserPartnerOrganization model
public function partnerOrganizations()
{
return $this->hasMany(PartnerOrganization::class);
}
And in PartnerOrganization
public function userPartnerOrganizations()
{
return $this->belongsToMany(UserPartnerOrganization::class);
}
And finally I am trying to go through the relationship to get a user_id when I know the partner_organization_id which I have in the $organization
$test = $organization
->partnerOrganization()
->first()
->userPartnerOrganizations()
->first();
The partnerOrganization relationship is working nicely but when I try to implement the userPartnerOrganizations I get this error in my log file
SQLSTATE[42S02]: Base table or view not found: 1146 Table 'homestead.partner_organization_user_partner_organization' doesn't exist in /home/vagrant/api/vendor/laravel/framework/src/Illuminate/Database/Connection.php:359
Don't understand where this strange table name is coming from or why the relationship is not working.

since your not following Laravel convention in tables name, you have to provide the pivot table name in relation declaration:
public function partnerOrganizations()
{
return $this->belongsToMany(PartnerOrganization::class,'user_partner__organization','user_id','partner_organization_id');
}
public function userPartnerOrganizations()
{
return $this->belongsToMany(UserPartnerOrganization::class,'user_partner__organization','partner_organization_id','user_id');
}
also note that the relation from both side should be belongsToMany
more about many to many relation in Laravel doc.

Related

Laravel relationship one to one doesnt work with single page view

I have created two models called video and file using Laravel 6.
A video can have only one file.
This is the relationship I created:
Video
public function file() {
return $this->hasOne('App\File');
}
File model
public function video() {
return $this->hasOne('App\Video');
}
If I loop all videos then I get the related media
#foreach($videos as $video)
{{$video->link->media}}
#endforeach
If I go to the related video single page it doesnt work.
{{$video->link->media}
Here the route:
Route::get('/video/{slug}', 'HomeController#singleVideo')->name('single');
I get following error:
Trying to get property 'media' of non-object
I also add the table Schema:
Schema::create('files', function (Blueprint $table) {
$table->bigIncrements('id');
$table->string('media')->default('none');
$table->unsignedBigInteger('video_id');
$table->timestamps();
});
Schema::create('videos', function (Blueprint $table) {
$table->bigIncrements('id');
$table->string('title',128);
$table->string('slug')->unique();
$table->text('description');
$table->string('url',247);
$table->string('category',128);
$table->unsignedBigInteger('views')->default(200);
$table->string('video_youtube_status')->default('off');
$table->string('video_status')->default('off');
$table->string('status')->default('off');
$table->timestamps();
});
Model Video
protected $guarded = [];
public function file() {
return $this->hasOne('App\File');
}
....
According to the Laravel documentation, the relation "hasOne" is not applied in this way, the primary model(let's say it's File) will have hasOne like in your code, but the secondary Model will have the Inverse Of The Relationship, which is 'belongsTo' so, in your video Model you should write:
public function file() {
return $this->belongsTo('App\File','file_id');
}
This will allows you to access to the entities like:
$video->file->some_property
$file->video->another_property
and another major problem in your videos table:
this table must have a foreign key to files table, which means:
in your videos migration you should add :
$table->unsignedBigInteger('file_id')->nullable(false);
$table->foreign('file_id')->references('id')->on('files');
According to Laravel documentation
You should implement the use of belognsTo relationship
and your query to get your results set must include the use of method with()
$users = User::with('podcasts')->get();
foreach ($users->flatMap->podcasts as $podcast) {
echo $podcast->subscription->created_at;
}

laravel hasMany polymorphic relationship in where clause

I am trying to select the picture with the most likes within a specific category from my database. I have a database table storing the pictures and a table storing the likes. The pictures table is related to likeable table through a hasMany polymorphic relationship.
Like model:
public function likeable()
{
return $this->morphTo();
}
Picture model:
public function likes()
{
return $this->morphMany('App\Like', 'likeable');
}
Home Controller:
Picture::where('picture_type', 'food')->orderBy(likes(), 'desc')->first();
Likeable Migration:
public function up()
{
Schema::create('likeable', function (Blueprint $table) {
$table->increments('id');
$table->integer('user_id');
$table->integer('likeable_id');
$table->string('likeable_type');
$table->timestamps();
});
}
So far, the above line of code, in my home controller returns an error. From what I understand, the likes method has to be called on a specific instance. However, I do not know how to implement this all the while keeping my where clause.
Thank you for your help.
I assume you are wanting to order pictures by the most likes.
In which case, you want something like this:
Picture::withCount('likes')->where('picture_type', 'food')->orderBy('likes_count', 'desc')->first();

get extra column with eloquent hasManyThrough

i have three tables cart , cart_products , products
i have that relation in cart table
public function products()
{
return $this->hasManyThrough(Product::class,CartProducts::class,'cart_id','id' )->withPivot('cart_products');
}
and this is my cart_products table
Schema::create('cart_products', function (Blueprint $table) {
$table->bigIncrements('id');
$table->unsignedInteger('product_id')
->references('id')->on('products')->onDelete('cascade');
$table->unsignedInteger('cart_id')
->references('id')->on('carts')->onDelete('cascade');
$table->unsignedInteger('quantity');
$table->timestamps();
});
i got all products finally , but i need to get quantity column with that realtion
any help?
Use the many to many relation with belongsToMany()
public function products()
{
return $this->belongsToMany(Product::class)->withPivot('quantity')->withTimestamps();
}
You may retrieve the qauantity column from the cart_products pivot table by passing the column name to the withPivot method
//...
return $this->belongsToMany('App\Product')
->using('App\CartProducts')
->withPivot('quantity');
See
Defining Custom Intermediate Table Models
in Docs

Eloquent Relationships Not Working as Expected

I am trying to understand what I am missing here.
Apps migration
Schema::create('apps', function (Blueprint $table) {
$table->increments('id');
$table->integer('show_id')->unsigned()->index();
$table->string('name');
$table->integer('provider_id')->unsigned()->index();
$table->timestamps();
});
Show migration
Schema::create('shows', function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->timestamps();
});
So I create an apps model that has the following function
public function Show() {
return $this->hasOne(Show::class);
}
But in php artisan tinker when I do $app->Show; I get the following error:
Illuminate\Database\QueryException with message 'SQLSTATE[HY000]: General error: 1 no such column: shows.app_id (SQL: select * from "shows" where "shows"."app_id" = 1 and "shows"."app_id" is not null limit 1)'
Am I mis-understanding the relationships?
Your relation should be as:
Apps model:
public function show() {
return $this->hasOne(Show::class, 'id', 'show_id');
}
Or it can be:
public function show() {
return $this->belongsTo(Show::class);
}
Docs
You do not have an app_id in your shows migration.
edit: Taking from the Laravel Docs and changing it to fit your situation
Eloquent determines the foreign key of the relationship based on the model name. In this case, the show model is automatically assumed to have a app_id foreign key.
A one-to-one relationship consists of a hasOne and a belongsTo. The table that contains the foreign key field must be on the belongsTo side of the relationship.
Since your apps table contains the show_id field, it is stated that apps belong to shows, and shows has one (or many) apps.
Given this, you need to change your Show relationship on your Apps model to use the belongsTo relationship.
public function Show() {
return $this->belongsTo(Show::class, 'show_id');
}
Unless you rename your relationship method so that it is lowercase (function show()), the second parameter is required. If you renamed the relationship, Laravel could build the proper key name and you could leave off the second parameter:
public function show() {
// For belongsTo, second parameter defaults to {function_name}_id.
return $this->belongsTo(Show::class);
}
In your apps model :
public function Show() {
return $this->belongsTo('yourmodelnamespace\Show','id','show_id');
}
And you need create Show model too ..
Hope it will works~~
You can use relation like this
public function Show() {
return $this->hasOne(Show::class, 'id','id');
}

How to retrieve Nested Relationship data in laravel 5 using eloquent?

Having some problems retrieving nested relationship data. Here are my models:
class Partner extends Model
{
public function admins()
{
return $this->hasMany(Resource::class)->where('resource_type', 'Admin');
}
}
class Resource extends Model
{
public function details() {
return $this->belongsTo(ResourceDetail::class);
}
}
class ResourceDetail extends Model
{
}
When I try $this->partner->admins[0]->details it's giving null. The sql it generated is: "select * from resource_details where resource_details.id is null". I'm not quite sure why is it null in the query. I must have done something wrong with the relations. I tried $this->partner->with('admins.details')->find($this->partner->id)->toArray();. It's getting the admins, but details is still null. I also tried hasManyThrough, like: return $this->hasManyThrough(ResourceDetail::class, Resource::class)->where('resource_type', 'Admin'); it finds "unknown column". This is my database structure:
Schema::create('partners', function (Blueprint $table) {
$table->increments('id');
});
Schema::create('resources', function (Blueprint $table) {
$table->increments('id');
$table->integer('partner_id')->nullable()->unsigned();
$table->foreign('partner_id')->references('id')->on('partners')
->onUpdate('cascade')->onDelete('set null');
$table->enum('resource_type', constants('RESOURCE_TYPES'))->nullable();
$table->integer('resource_detail_id')->unsigned();
$table->foreign('resource_detail_id')->references('id')->on('resource_details')
->onUpdate('cascade')->onDelete('cascade');
});
Schema::create('resource_details', function (Blueprint $table) {
$table->increments('id');
});
Do I need to change the structure? Or, how can I get the data from current structure? All I want is, a partner has many resources, and a resource has one details.
From that error I think you may be trying to call $this->partner->admins[0]->details from a model that doesn't have an id. What is $this in context to?

Resources