I believe you code will fail at the following lines:
$qb = array_values(collect(array_merge($qb, $favorite_posts))
->sortByDesc('created_at')->toArray());
$posts = array_merge($favorite_posts, $qb);
You are merging the $favourite_posts array with $qb, an instance of Illuminate\Database\Eloquent\Builder class.
Reading your code, I think you want to get posts that:
- paginated and sorted by the input.
- created by the user and all his following.
- reposted by the user and all his following.
When a feature involves pagination, I suggest creating a main query, then get the count and paginated results in the end.
I think you code can be refactored to this, I rename some variables to my likings:
$limit = (isset($input['limit'])) ? $input['limit'] : $this->per_page;
$sortBy = (isset($input['sort_by'])) ? $input['sort_by'] : 'created_at';
$sortOrder = (isset($input['sort_order'])) ? $input['sort_order'] : 'desc';
$query = Post::orderBy($sortBy, $sortOrder);
$dataType = 'Posts';
if (isset($input['user_id'])) {
$dataType = 'Feed';
$user = User::find($input['user_id']);
$userIds = $user->followings->push($user)->pluck('id')->toArray();
$query->selectRaw('posts.*, fav_posts.user_id as reposted_user_id, fav_posts.created_at as reposted_at')
->join('fav_posts', 'posts.id', '=', 'fav_posts.post_id')
->whereIn('user_id', $userIds)
->orWhereIn('reposted_user_id', $userIds);
}
return [
'data' ⇒ $query->paginate($limit),
'header' => [
'status' => $data_type . ' retrieved successfully',
'pages' => $this->getPages($total, $limit),
'page' => isset($input['page']) ? +$input['page'] : 1,
'total' => $query->count(),
]
];