$user = User::where('id', $id)->with(['experiences_user'])->first();
dd($user->experiences_user());
When i execute dd it's not showing the values of relationship have.
relations: array:1 [▼
"experiences_user" => Collection {#196 ▼
#items: []
}
User Model Relationships:
public function experiences_user(){
return $this->hasMany('App\experiences', 'User_id');
}
Experiences Model Relationships:
public function employee(){
return $this->belongsTo('App\User','User_id', 'id');
}
Try lazy loading:
$user = User::where('id', $id)->first()->load('experiences_user');
Related
in our web application we want to have a simple package base cms, for having that we have users, packages, features and user_package table on database
each users can be have one package which we created
user_package for that
each user_package belongs to many users
each user_package has on packages
each packages can be have many features which we created
features table
each features belongs to many packages
when i try to get user package it, i think it should be:
user->user_package->package->[feature]
my models:
class User extends Authenticatable
{
//...
public function user_package()
{
return $this->hasOne(UserPackage::class);
}
}
class UserPackage extends Model
{
public function package()
{
return $this->belongsTo(Package::class);
}
}
class Package extends Model
{
public function feature(): HasMany
{
return $this->hasMany(Features::class);
}
}
class Features extends Model
{
public function package(): BelongsToMany
{
return $this->belongsToMany(Package::class);
}
}
migrations:
Schema::create('packages', function (Blueprint $table) {
$table->id();
$table->string('title');
$table->text('description')->nullable()->default('');
$table->timestamp('created_at')->useCurrent();
$table->timestamp('updated_at')->useCurrent();
});
Schema::create('features', function (Blueprint $table) {
$table->id();
$table->foreignId('packages_id')->nullable()
->constrained()->cascadeOnUpdate()
->cascadeOnDelete();
$table->string('title');
$table->text('description')->nullable()->default('');
$table->timestamp('created_at')->useCurrent();
$table->timestamp('updated_at')->useCurrent();
});
Schema::create('user_packages', function (Blueprint $table) {
$table->id();
$table->foreignId('user_id')->constrained()
->cascadeOnUpdate()
->cascadeOnDelete();
$table->foreignId('packages_id')->nullable()->constrained()
->cascadeOnUpdate()
->cascadeOnDelete();
$table->longText('features')->nullable()->default('');
$table->integer('price');
$table->dateTime('start_date');
$table->dateTime('end_date');
$table->timestamp('created_at')->useCurrent();
$table->timestamp('update_at')->useCurrent();
});
now when i try to get data i get null in package relation ship
Route::get('/test',function(){
dd(auth()->user()->with(['user_package'=>function($query){
$query->with(['package'=>function($package){
$package->with('feature')->get();
}])->first();
}])->first());
});
output:
App\Models\User {#1319 ▼
#hidden: array:2 [▶]
#casts: array:1 [▶]
#connection: "mysql"
#table: "users"
...
#relations: array:1 [▼
"user_package" => App\Models\UserPackage {#1570 ▼
#connection: "mysql"
#table: "user_packages"
...
#dispatchesEvents: []
#observables: []
#relations: array:1 [▼
"package" => null
]
...
}
I think the crux of your question comes down to fetching nested relationships, which is as simple as auth()->user()->with('user_package.package.feature') but there is a problem with your relationships.
Your relationship between Package and Feature is broken; since the features table has a package_id column, a feature by definition cannot "belong to many" packages.
class User extends Authenticatable
{
public function user_package(): HasOne
{
return $this->hasOne(UserPackage::class);
}
}
class UserPackage extends Model
{
public function user(): BelongsTo
{
return $this->belongsTo(User::class);
}
public function package(): BelongsTo
{
return $this->belongsTo(Package::class);
}
}
class Package extends Model
{
public function features(): HasMany
{
return $this->hasMany(Feature::class);
}
/**
* It never hurts to define both ends of the relationship
* even if they aren't being used
*/
public function user_packages(): HasMany
{
return $this->hasMany(UserPackage::class);
}
}
class Feature extends Model
{
public function package(): BelongsTo
{
return $this->belongsTo(Package::class);
}
}
Now, using the relationship, you can get the package features:
dump(Auth::user()->load('user_package.package.features'))
You've got some naming problems that I corrected in my examples above – relationship methods that return a single model should be singular, others should be plural. Class names should never be plural words (i.e. Feature not Features.)
Generally speaking, there's no need to create a pivot class if all it's doing is connecting two models. I'm not going to get into that since it would make for a much longer answer, but it's something to keep in mind.
And it's a matter of personal taste, but your class names should be one word only (i.e. Subscription instead of UserPackage) as it makes figuring out things like relationship names more intuitive.
I have this query
$products = DB::table('product_attributes')
->where('product_attributes.attribute_id', '=', $attri->id)
->joinoin('products', 'products.id', '=',
->get();
and it returns
Collection {#2788 ▼
#items: array:2 [▼
0 => {#2785 ▶}
1 => {#2786 ▶}
]
}
but then I don't have access to my products cover image, so I changed my query to:
$products = DB::table('product_attributes')
->where('product_attributes.attribute_id', '=', $attri->id)
->join('products', 'products.id', '=', 'product_attributes.product_id')
->join('covers', 'covers.imageable_id', '=', 'products.id')
->get();
and it returns:
Collection {#2805 ▼
#items: []
}
empty!
Again I changed my query to:
$products = DB::table('product_attributes')
->where('product_attributes.attribute_id', '=', $attri->id)
->leftJoin('products', 'products.id', '=', 'product_attributes.product_id')
->leftJoin('covers', 'covers.imageable_id', '=', 'products.id')
->get();
and it returns:
Collection {#2807 ▼
#items: array:2 [▼
0 => {#2804 ▶}
1 => {#2805 ▶}
]
}
yet without having access to my covers (same as my first query).
question
How can I have access to my products with all other models relations?
More...
here is some of other relations to my product model
public function covers()
{
return $this->hasMany(Cover::class, 'imageable_id');
}
public function photos()
{
return $this->hasMany(Photo::class, 'imageable_id');
}
public function options(){
return $this->belongsToMany(Option::class, 'product_options', 'product_id', 'option_id');
}
public function attributes(){
return $this->belongsToMany(Attribute::class, 'product_attributes', 'product_id', 'attribute_id');
}
public function categories(){
return $this->belongsToMany(Category::class, 'product_categories', 'product_id', 'category_id');
}
If you have the relationships set-up you could do it in the following way:
$products = Product::with(['covers','attributes'])->whereHas('attributes', function ($query) use ($attri) {
$query->where('product_attributes.attribute_id', $attri->id);
})->get();
This way you get all your products which have an attribute with the given identifier and along with those products you will also retrieve the covers and attributes.
To access a cover or attribute in the first product for example you could do $products->first()->covers
Init only main object
$product = Product::findOrFail($id);
Use relations as object. Not use query-builder.
$product->covers();
$product->photos();
Recently I've been trying to create Nova resource which depends on the other resource which provides the information for the main resource.
I have a table contest_entries which has the following fields:
id
contest_id
user_id
with the following relations
public function contest() : BelongsTo {
return $this->belongsTo(Contest::class, 'contest_id', 'id');
}
public function user() : BelongsTo {
return $this->belongsTo(User::class, 'user_id', 'id');
}
Also, i have a table contest_submissions with the following fields:
id
entry_id
task_id
comment
approved
declined
with the following relations:
public function entry() : BelongsTo {
return $this->belongsTo(ContestEntry::class, 'entry_id', 'id');
}
public function user() : BelongsTo {
return $this->entry->user();
}
public function contest() : BelongsTo {
return $this->entry->contest();
}
public function task() : BelongsTo {
return $this->belongsTo(Task::class, 'task_id', 'id');
}
I have no problem in fetching this data on the index and details view of Nova, everything 'just works', however, when I try to update the resource, I'm getting the error that user() or contest() is called on null.
I've tried the following,
return [
BelongsTo::make('Contest', 'contest', Contests::class)->exceptOnForms(),
BelongsTo::make('Task', 'task', ContestTasks::class)->exceptOnForms(),
BelongsTo::make('User', 'user', AccountUsers::class)->exceptOnForms(),
]
But for some reason, Nova is still trying to fetch these relationships ever when i explicitly tell it not to.
Any ideas are greatly appreciated, because it works everywhere, except on the update view (create view is explicitly disabled since the submissions are created by the user on the frontend)
You should also chain a hideWhenUpdating() constraint to it.
return [
BelongsTo::make('Contest', 'contest', Contests::class)
->hideWhenUpdating()
->exceptOnForms(),
BelongsTo::make('Task', 'task', ContestTasks::class)
->hideWhenUpdating()
->exceptOnForms(),
BelongsTo::make('User', 'user', AccountUsers::class)
->hideWhenUpdating()
->exceptOnForms(),
]
So I am trying to attach an object full of information from the MYSQL DB, but the outcome isn't what I am expecting.
Controller -
public function index()
{
$location = Location::orderBy('created_at', 'desc');
return view('location')->with('locations', $location);
}
Model -
class Location extends Model
{
// Primary Key
public $primaryKey = 'id';
// Timestamps
public $timestamps = true;
}
Result -
Builder {#486 ▼
#query: Builder {#485 ▶}
#model: Location {#484 ▶}
#eagerLoad: []
#localMacros: []
#onDelete: null
#passthru: array:12 [▶]
#scopes: []
#removedScopes: []
}
Change this
$location = Location::orderBy('created_at', 'desc');
To
$location = Location::orderBy('created_at', 'desc')->get();
When using $location = Location::orderBy('created_at', 'desc'); it is a instance of Illuminate\Database\Query\Builder.
For get all records you must use
$locations = Location::orderBy('created_at', 'desc')->get();
It is return instance of \Illuminate\Database\Eloquent\Collection
For get Limited records you must use
$limit = 20; // or custom
$limitedLocations = Location::orderBy('created_at', 'desc')->limit($limit)->get();
For get single data use
$location = Location::orderBy('created_at', 'desc')->first();
It is return null or instance of model Location
So I'm basically trying to retrieve all "favourites" for a specific user from the pivot table favourite (yes it seems that I started my project by misspelling the word favorite).
So when viewing u/Admin, I should be able to view all games admin has favorited.
public function index(User $user)
{
$favourites = Auth::user()->favourites;
// dd($favourites);
return view('u.index', compact('favourites'));
}
But when dd($favourite);, I'm returned a empty collection.
Collection {#216 ▼
#items: []
}
in m y Users.php i have the following:
public function getRouteKeyName()
{
return 'name';
}
public function favourites()
{
return $this->belongsToMany(Game::class, 'favourites', 'user_id', 'game_slug')->withTimeStamps();
}
Might it have something to do with that Game.php has it route key set to the slug?
public function getRouteKeyName()
{
return 'slug';
}
Try this:
Create a model called 'Favourite'(make sure you have a user_id column in the favourites table)
put this in your controller -> use App\Favourite;
And try this code:
$user_id = Auth::user()->id;
$favourites = Favourite::where('user_id', $user_id)->get();