Merging two queries into one using Eloquent - laravel

I have this two queries to display information in 3 tables Users, Comments, and Posts. so I made this function:
public function show($id)
{
$posts = Post::with(['comments'])->findOrFail($id);
$user = User::find($posts->user_id);
echo "<h1>".$posts->title.'</h1>';
echo "<h2>".$user->name.'</h2>';
foreach ($posts->comments as $comment) {
echo $comment->body.'<br>';
}
}
on this function I using two variable $posts and $user, can I merge this two variable using eloquests command like Post::with(['user','comments'])'? so I can use just $posts variable and use it like $posts->users->name to access user name.
i was trying using this way:
$posts = Post::with(['comments','users'])->findOrFail($id);
but when i echo the post it showing that the user was null:
{"id":1,"user_id":1,"title":"Oleh id 1","body":"ini adalah content","created_at":"2017-10-18 03:25:54","updated_at":"2017-10-18 03:25:54","comments":[{"id":1,"post_id":1,"body":"Keren banget deh artikelnya, TOP","created_at":"2017-10-18 03:43:50","updated_at":"2017-10-18 03:43:50"},{"id":2,"post_id":1,"body":"Keren banget deh artikelnya, TOP","created_at":"2017-10-18 03:43:53","updated_at":"2017-10-18 03:43:53"},{"id":3,"post_id":1,"body":"Keren banget deh artikelnya, TOP","created_at":"2017-10-18 03:43:54","updated_at":"2017-10-18 03:43:54"}],"users":null}
Here's my model if you need it. My post model:
class Post extends Model
{
/**
* Get the comments for the blog post.
*/
public function comments()
{
return $this->hasMany('App\Comment');
}
public function users(){
return $this->belongsTo('App\User');
}
}
my Comment model
class Comment extends Model
{
/**
* Get the post that owns the comment.
*/
public function post()
{
return $this->belongsTo('App\Post');
}
}

You’ll have an easier time sticking to Laravel’s conventions for naming relationships.
A Post has many Comments, which belong to a User. Given this set up:
class Post extends Model
{
public function comments()
{
return $this->hasMany(Comment::class);
}
}
class Comment extends Model
{
public function post()
{
return $this->belongsTo(Post::class);
}
public function user()
{
return $this->belongsTo(User::class);
}
}
You can then query a post’s comments and users like this:
$comments = $post->comments()->with('user')->get();
You could also eager-load the user relation on comments if you always wanted the user returned with a comment:
class Comment extends Model
{
protected $with = ['user'];
public function user()
{
return $this->belongsTo(User::class);
}
}
Then your query would be simplified:
$comments = $post->comments;
Hope this helps you!!

What I am guessing is you want the list of all posts with the users. If relation is defined, try with the join
$posts = DB::table('posts')
->join('users', 'users.id', '=', 'posts.user_id')
->select('posts.*', 'users.name as user_name')
->where('posts.comments', '<>', NULL)
->get();
#NOTE: If you are using soft deletes you might wanna add where('posts.deleted_at', null)

After couple of days searching finally i got the answer, i can get merge the query like this:
$posts = Post::with(['comments','users'])->findOrFail($id);
but in the Post Model the function not "Users" but "User".

Related

Getting specific value when using eloquent from Laravel

I am using Laravel 5.2 and I need to get specific values from the database with a leftjoin. The code I am using is as follow:
public function commentList(Request $request)
{
$inputs = $request->all();
$commentList = Comment::select(
'projects_comments.id as comment_id',
'u.name as user_name',
'projects_comments.comment as comment',
'projects_comments.created_at as created_at'
);
$commentList->leftjoin('users AS u', 'projects_comments.user_id', '=', 'u.id');
if (!empty($inputs['project_ids'])) {
$commentList->where(function ($query) use ($inputs) {
foreach ($inputs['project_ids'] as $i) {
$query->orWhere('projects_comments.project_id', $i);
}
});
};
$data = $commentList->get();
return $data;
}
It works fine but I would like to know if there is a better way to do this using eloquent but I can't really understand how to write this for eloquent to work. I need to get all the comments from an array of project ids.
I have the following model for Comment:
class Comment extends Model
{
protected $table = 'projects_comments';
public $timestamps = true;
protected $guarded = ['id'];
public function project()
{
return $this->belongsTo('App\Project', 'project_id');
}
public function user()
{
return $this->belongsTo('App\User', 'user_id');
}
}
I assume what you want is to get Comments (with their users) that belongs to specific Projects provided by the user as an array of IDS
Comment::whereIn('project_id', $inputs['project_ids'])->with('user')->get();
And if you only want the id and name of the user associated with the comment, pass the fields to the with function like so
Comment::whereIn('project_id', $inputs['project_ids'])
->with('user:id,name')->get();

Laravel 5 - Eloquent: easier way to filter a many to many relationship

I have a many to many relationship between Lists and Users.
This is the List Model:
class ListModel extends Model
{
protected $table = "lists";
public function users()
{
return $this->belongsToMany('App\Models\User', 'list_user', 'list_id', 'user_id')->withTimestamps();
}
}
This is the User model:
class User extends Authenticatable
{
public function lists()
{
return $this->hasMany('App\Models\ListModel');
}
}
In a list page, I need to get all the lists belonging to the logged user. The only solution I found is this one:
$user = \Auth::user()->id;
$all_lists = ListModel::whereHas('users', function ($query) use ($user) {
$query->where('user_id', $user);
})->active()->get();
is there any simpler way to achieve the same result?
Since current user is already loaded, you can use lazy eager loading to load lists for the user:
auth()->user()->load('lists');
Your lists() relationship is not defined correctly. The inverse of belongsToMany is still belongsToMany (hasMany's inverse is belongsTo):
class User extends Authenticatable
{
public function lists()
{
return $this->belongsToMany('App\Models\ListModel', 'list_user', 'user_id', 'list_id')->withTimestamps();
}
}
Then you can get the lists like this:
$user = \Auth::user();
$all_lists = $user->lists()->active()->get()

Eloquent query - one to many relationship

Guys I'm new to Laravel and I'm trying to find the name of the user that answers a certain question:
$users = User::with('answers')->where('question_id', $request->question_id)->get();
I've tried this but it doesn't work.It seems like he is trying to find the question_id from the User and not from the Answer.
Answer Model
Class Answer extends Model{
public function users()
{
return $this->belongsTo(User::class);
}
}
User Model
Class User extends Authenticatable{
public function answers()
{
return $this->hasMany(Answer::class);
}
}
This is what you need, Constraining Eager Loads.
$users = User::with(['answers' => function ($query) use ($request) {
$query->where('question_id', $request->question_id)
}])->get();
This is not what you asked for but maybe what you need:
$answers = Answer::with('user')->where('question_id', $request->question_id)->get();

How to use one to many relation in Laravel?

I'm beginning to use Laravel Model relationship. But now I don't know how to used that relationship as below function
class Notification extends Model{
public function getNotification() {
return self::select('*')->join('users','users.id','=','Notification.n_user_id')->get();
}
}
Try this:
class User extends Model
{
/**
* Get the Notifications for the User.
*/
public function notifications()
{
return $this->hasMany('App\Notification');
}
}
But I see in your code that the foreign key field of User ID is named n_user_id you should changed it to user_id to link them
How to use:
$notifications = App\Post::find(1)->notifications;
foreach ($notifications as $notification) {
//
}
here is a useful Link in Laravel 5.2 Docs
Bonus:
You can also get the User of the notification:
class Notification extends Model
{
/**
* Get the User that owns the Notification.
*/
public function user()
{
return $this->belongsTo('App\User');
}
}
I have used the following way and hope it'd be helpful.
public function getNotification() {
$data = DB::table('users')
->join('Notification', 'users.id', '=', 'Notification.n_user_id')
->select('users.*', 'Notification.*')
->where('users.id', '=', 5)
->get();
return $data;
}

Laravel eloquent in dedicated relation table?

How to get multiple row from tags table using single id_post in eloquent.
I think you need to set a Many to many relation in your post and tag model:
Your Post Model:
public function tags()
{
return $this->belongsToMany('Tag');
}
Your Tag model:
public function posts()
{
return $this->belongsToMany('Post');
}
And then you can use Eloquent to get all tags associated to your post_id:
$tags = Post:find($post_id)->tags()->get();
$posts = Post::with('tags')->get();
foreach($posts as $post) {
$tags = $post->tags;
}
Now, this is assuming that you've setup your models as 'Post' and 'Tag'
If your Post model, you should have a tags method that says where to find the tags, something like:
public function tags()
{
return $this->belongsToMany('Tag');
}

Resources