maybe this is a simple problem but for me, am I newbie in Laravel, it's problem, so I have three table
Articles, User, Comments. They have this relationship
In page http://localhost/users/{user_name} I want to get all articles and all comments that belongs to this user.
Three Model looks like this:
User
public function articles()
{
return $this->hasMany('App\Article');
}
public function comments()
{
return $this->hasMany('App\Comment');
}
Article
public function user()
{
return $this->belongsTo('App\User');
}
public function comments()
{
return $this->hasMany('App\Comment');
}
and
Comment
public function user()
{
return $this->belongsTo('App\User');
}
public function article()
{
return $this->belongsTo('App\Article');
}
My Controller Show method looks like this:
public function show(User $user)
{
$user->with(['comments','articles'])->get();
return view('users.show', compact('user', 'comments', 'articles'));
}
In view I have everything what I need
{{ dump($user) }}
{{ dump($user->articles) }}
{{ dump($user->comments) }}
{{ dd() }}
and with foreach I get needed attributes, but how do I create link where I can see link to article and comment to her
#foreach($user->comments as $comment)
<div class="block">
//article title
<div></div>
<div>{{ $comment->comment }}</div>
#endforeach
To show article I use title of article, not ID.
Thanks
First, 'comments' and 'articles' here don't do anything.
return view('users.show', compact('user', 'comments', 'articles'));
As for the link,
{{ $comment->article->title }}
I resolved this issue, updated my controller:
public function show(User $user)
{
$params = Comment::where('user_id', $user->id)->get()
return view('users.show', compact('user', 'params'));
}
It's works like I need but I think that there are better way to resolve this.
Related
should I give id for posts? How Laravel know which comments belong to which post?
This is my controller :
public function show($id){
$posts=Post::where('id',$id)->get();
return view('user',compact('posts'));
}
This is my blade :
#foreach($posts->comments as $comment)
<div class="comment-form">
<section class="post-body">
<p>{{ $comment->description }}</p> <!-- burda ilisdim -->
</section>
</div>
#endforeach
So I built polymorphic relations about comments. but I don't know how to use it.
UPDATE
here is my Post Model
public function comments()
{
return $this->morphMany('App\Comment', 'commentable');
}
}
You need to define the relation on Post model, as like :
public function comments()
{
return $this->hasMany(Comment::class);
}
Then you can access like this :
#foreach($posts->comments as $comment) // $posts->comments will call your comments() function
{{ $comment->description }}
#endforeach
As I can see you doing something wrong. Please replace your code with below:
To Get Single post you have to replace code with given below in controller
public function show($id){
$posts=Post::where('id',$id)->first();
return view('user',compact('posts'));
}
I am trying to displaying the book a user has favorited, so I think many to many relationships will solve it. So I have 3 tables
Users Table
Books Table
Favorite Table
The Favorite table is the pivot table
Schema::create('favorites', function (Blueprint $table) {
$table->bigIncrements('id');
$table->integer('book_id')->unsigned();
$table->integer('user_id')->unsigned();
$table->timestamps();
});
In the User Model
public function favorites(){
return $this->hasMany(Favorite::class);
}
In the Book Model
public function favorites()
{
return $this->hasMany(Favorite::class);
}
In my Favorite Model
public function book ()
{
return $this->belongsTo(Book::class);
}
I was able to save to Favorite Column like this
public function favorite($id)
{
Favorite::create([
'book_id' => $id,
'user_id' => Auth::id()
]);
Session::flash('success', "You Favorite a Book");
return redirect()->back();
}
But I am trying to show the Books Favorited
public function mylibrary(){
$user = Auth::user()->books;
// dd($user);
return view('library', compact('user'));
}
In my view, I have this
#foreach($user->books as $mybook)
...
<div class="clearfix"></div>
<p class="authorone">{{ $mybook->author->name }}</p>
<h1 class="book-title">{ $mybook -> title }}</h1>
</div>
#endforeach
You are passing Auth::user()->books to your view, not Auth::user(). You are not passing the User.
In the view you are then trying to use that value as an object:
#foreach ($user->books as $mybook)
Auth::user()->books is most likely returning null since it is not a relation method or an attribute (most likely).
You probably want to pass the User to your view:
view(..., ['user' => Auth::user()]);
Then you would want to access the correct dynamic property for the relationship you want since you aren't showing a books relationship on User.
Your model relationships could use a better setup. There is no Many to Many setup here and you don't need to define a model for the pivot, you are actually avoiding the Many to Many by doing this.
Models:
class User
{
public function books()
{
return $this->belongsToMany(Book::class, 'favorites');
}
}
class Book
{
public function users()
{
return $this->belongsToMany(User::class, 'favorites');
}
}
Controller:
public function favorite($id)
{
Auth::user()->books()->attach($id);
...
}
public function mylibrary()
{
$user = Auth::user()->load('books.author');
return view('library', compact('user'));
}
View:
#foreach($user->books as $mybook)
...
<div class="clearfix"></div>
<p class="authorone">{{ $mybook->author->name }}</p>
<h1 class="book-title">{{ $mybook->title }}</h1>
</div>
#endforeach
I was able to solve it this way
My view
#forelse ($user->favorites as $mybook)
<p class="authorone">{{ $mybook ->book->author-> name }}</p>
<h1 class="book-title">{{ $mybook ->book-> name }}</h1>
#empty
<h2>You haven't Favorited any book</h2>
<div class="text-center">
Return To
</div>
#endforelse
I added this to my user model
public function favorites(){
return $this->hasMany(Favorite::class);
}
public function books()
{
return $this->belongsToMany(Book::class);
}
My controller
public function mylibrary(){
return view('library', ['user' => Auth::user()]);
}
I'm creating a functionality which allows the user to add product in wishlist, but I'm getting an error Trying to get property of non-object when I click the (whishlist blade), the error comes from this line <h4>USD {{$wishlist->product->price }}</h4> if I remove the $product it displays no price how do i fix this?
Wishlist Controller
public function index()
{
$user = Auth::user();
$wishlists = Wishlist::where("user_id", "=", $user->id)->orderby('id', 'desc')->paginate(10);
return view('wishlist', compact('user', 'wishlists'));
}
Blade
#if (Auth::user()->wishlist->count() )
#foreach($wishlists as $wishlist)
<h2>USD {{$wishlist->product->price }}</h2>
<h4>USD {{$wishlist->product->name }}</h4>
#endforeach
#endif
Wishlist.php
class Wishlist extends Model
{
protected $table = "wishlist";
protected $fillable=['product_id','user_id'];
public function user(){
return $this->belongsTo(User::class);
}
public function product(){
return $this->belongsTo(Product::class);
}
}
User.php
public function wishlist(){
return $this->hasMany(Wishlist::class);
}
Product.php
public function wishlist(){
return $this->hasMany(Wishlist::class);
}
You should first change how you check the count of wishlist, since it runs a heavy query that recovers all wishlists then count them. And also remove the $ in $product as #lucasArbex suggested
#if ($wishlists->count() )
#foreach($wishlists as $wishlist)
<h2>USD {{$wishlist->product->price }}</h2>
<h4>USD {{$wishlist->product->name }}</h4>
#endforeach
#endif
Also change your controller and use the relation on your user
public function index()
{
$user = Auth::user();
$wishlists = $user->wishlist()->with('product')
->orderby('id', 'desc')
->paginate(10);
return view('wishlist', compact('user', 'wishlists'));
}
Firstly, you should access the product relation like so (removing $):
$wishlist->product->price
Secondly, you should eager load the wishlist's product using the ::with() query builder:
public function index()
{
$user = Auth::user();
$wishlists = Wishlist::with('product')
->where('user_id', $user->id)
->orderby('id', 'desc')
->paginate(10);
return view('wishlist', compact('user', 'wishlists'));
}
Also, if I am correct, your product relation is wrong.
Your wishlist should have many products (rather than the other way around).
In your frontend, you will need to loop through all of the wishlist's products:
#foreach($wishlist->products as $product)
{{ $product->price }}
#endforeach
Change the relation in your Wishlist class to hasMany:
public function products()
{
return $this->hasMany(Product::class);
}
I have a blog and want to include the Users Name when shown to the public.
When creating the blog I make sure to include the user_id in the blogs table
In my Blog model I have the following:
public function users()
{
return $this->belongsTo(User::class);
}
In my Users model I have:
public function blogs()
{
return $this->hasMany(Blog::class);
}
In my Blog Controller I have:
public function index(User $user)
{
$users = User::get();
$blogs= DB::table('blogs')->where('user_id', '=', $users->id)->orderBy('id', 'DESC')->paginate(6);
return view('blogs.index',compact('blogs'));
}
Then in my view:
#foreach($blogs as $blog)
<h1>{{$blog->title}}</h1>
Source:{{$blog->users->first_name}} // This does not work
Source:{{$blog->first_name}} // This does not work either
#endforeach
I thought I could do something like this to show the names:
{{ $blogs->users->first_name }} {{ $blogs->users->last_name }}
But this isn't working either...
Try this:
#foreach($blogs as $blog)
<h1>{{$blog->title}}</h1>
{{$blog->user->first_name}}
#endforeach
And on your Blog Model
public function user()
{
return $this->belongsTo(User::class);
}
In your Blog controller the variable $blog needs to be $blogs. You also have extra characters (right parenthesis) in your Blade. It should be:
#foreach($blogs as $blog)
Source: {{ $blog->user->first_name }}
...
#endforeach
Blog Model
This function replaces the old "users" function, as only one user is returned (belongsTo is a singular relationship).
class Blog extends Model
{
public function user()
{
return $this->belongsTo('App\User');
}
}
User Model
public function blogs()
{
return $this->hasMany('App\Blog');
}
Controller Function
And, as such, you can cut down your controller code, including removing the redundant elements.
public function index(User $user)
{
$blogs = Blog::where('user_id', '=', $user->id)->orderBy('created_at','desc')->paginate(6);
return view('blogs.index', compact('blogs'));
}
The way you did is called Query Builder
$blogs= DB::table('blogs')->where('user_id', '=', $users->id)->orderBy('id', 'DESC')->paginate(6);
Query Builder does not support lazy loading, cause lazy loading is only supported for the Eloquent method
$blog->users->first_name
For Eloquent way you can try this instead:
$blogs = Blog::where('user_id', $user->id)->get()
foreach($blogs as $blog){
dd($blog->user); // you will get the user detail here
}
For lazy loading have a performance issue when come to load heavy data so to prevent lazy loading can use this
$blogs = Blog::with('user')->where('user_id', $user->id)->get()
For more information can look at Eloquent Relationship Documentation
For query builder, the only way to link your user is use join, which will be something like this
$blogs = DB::table('blogs')
->join('users', 'users.id', '=', 'blogs.user_id')
->get();
foreach($blogs as $blog){
dd($blog->first_name) // user first name
}
For more information can look at Query Builder Join
BlogController.php
public function index(){
$blogs = Blog::with('user')->get();
return view('blogs.index')->with('blogs',$blogs);
}
Blog.php
public function user()
{
return $this->belongsTo('App\User');
}
User.php
public function blogs()
{
return $this->hasMany('App\Blog');
}
I want to make a user wall where all of his post will be loaded with those who has given comment under it. So I have defined following relations in my User model.
public function post()
{
return $this->hasMany(Post::class);
}
public function comment()
{
return $this->hasMany(Comment::class);
}
My Post model:
public function user()
{
return $this->belongsTo(User::class);
}
public function post_comment()
{
return $this->hasMany(Comment::class);
}
My Comment model:
public function user()
{
return $this->belongsTo(User::class);
}
public function post()
{
return $this->belongsTo(Post::class);
}
In my Controller:
public function wall($id)
{
$all_post = Post::where('user_id',$id)->get();
return view('client.wall',['all_post'=> $all_post]);
}
in my Blade file:
#foreach($all_post as $post)
Post Title: {{ $post->title }} //gets the title properly
#foreach($post->post_comment as $comment) //this foreach loop throwing erros
Name: {{ $comment->user->name }}
Comment: {{ $comment->description }}
#endforeach
#endforeach
Probably my logic is wrong to load the comments from database. Because I am getting errors.
try this ad share if you still have an error
Controller
public function wall($id)
{
$all_post = Post::where('user_id',$id)->with('post_comment')->get();
return view('client.wall')->with('all_post',$all_post);
}
VIEW
#foreach($all_post as $post)
Post Title: {{ $post->title }} //gets the title properly
#foreach($post->post_comment as $comment)
Name: {{ $comment->user->name }}
Comment: {{ $comment->description }}
#endforeach
#endforeach