0

I am trying to write a MySQL select query using Laravel's Database Query Builder

I have this mysql query:

 SELECT * FROM `tweets` WHERE `user_id` = 1 OR `user_id` in (SELECT `follows_id` from `follows` where `user_id` = 1)

I am trying to write it for Laravel

$users = DB::table('tweets')
         ->where('user_id', '=', 1)

how can this be done?

5
  • Look into defining relationships. Define a Tweet model, a User model and associate them, then you should be able to do $result = Tweet::whereHas("User", function($subQuery){ $subQuery->where("user_id", "=", 1); })->get(); Commented Jun 11, 2019 at 15:40
  • Before following @TimLewis 's suggestion, i would suggest rewritting this query into SELECT * FROM tweets WHERE tweets.user_id = 1 UNION ALL SELECT * FROM tweets INNER JOIN follows ON tweets.user_id = follows.follow_id WHERE follows.user_id = 1 as it is more optimal if performance matters OR and IN(SELECT ..) tends to optimize to bit badly in MySQL. Commented Jun 11, 2019 at 15:43
  • I agree with both comments, as for the @TimLewis one, it won't work, because as far as I understand from the query what he tries to get is a list of all tweets for the user AND tweets from users that the logged in user follows. Correct me if I am wrong. Commented Jun 11, 2019 at 15:45
  • 1
    @nakov True, but that can be an additional orWhereHas() clause. It's a little hard to answer this in Laravel terms due to having to guess at the relationships/query logic. I try to avoid the usage of DB::table() in favour of Models, but your answer should work fine. Commented Jun 11, 2019 at 15:47
  • nakov yes you are write thats exactly what i am trying to do Commented Jun 11, 2019 at 15:49

2 Answers 2

2

You can do something like this even though it looks ugly.

$tweets = DB::table('tweets')
         ->where('user_id', 1)
         ->orWhereIn('user_id', DB::table('follows')->select('follows_id')->where('user_id', 1)->pluck('follows_id'))
         ->get();

Sign up to request clarification or add additional context in comments.

Comments

1

I would suggest a SQL rewrite as OR and IN(SELECT ...) tends to optimize badly.
The SQL result might be wrong as you didn't provide example data and expected result see Why should I provide a Minimal Reproducible Example for a very simple SQL query? for providing those.

SELECT
  tweets.*
FROM
  tweets
WHERE
 tweets.user_id = 1

UNION ALL

SELECT
  tweets.*
FROM
 tweets
INNER JOIN
 follows ON tweets.user_id = follows.follows_id
WHERE
 follows.user_id = 1

I believe the following Laraval code should do that. But not sure as i didn't program in Laravel for some time now.

<?php
 $first = DB::table('tweets')
            ->select('tweets.*')
            ->where('user_id', '=', 1); 

 $second = DB::table('tweets')
             ->select('tweets.*')

             ->join('follows', 'tweets.user_id', '=', 'follows.follows_id')
             ->where('follows.user_id ', '=', 1)

            ->union($first)
            ->get();
?> 

1 Comment

Works like charm!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.