【问题标题】:Exclude results from query if relationship in table exists如果表中存在关系,则从查询中排除结果
【发布时间】:2022-03-10 12:43:49
【问题描述】:

我有两张桌子:

posts表:

id | user_id | message
----------------------
 1 |      24 | hello
 2 |      96 | world
...

posts_seen表:

id | user_id | post_id
----------------------
 1 |      24 |       2
 2 |      96 |       1

第二个表posts_seen 仅跟踪用户“看到”(或阅读)了哪些帖子。例如,用户 #24 看过帖子 #2。

在我的Post.php 模型中,我有这个:

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Post extends Model
{
    protected $table = 'posts';

    public function seen()
    {
        return $this->hasOne('App\Models\PostSeen');
    }
}

但是,当我查询帖子时,我想排除用户已经看过的帖子。现在,我只有这个:

$posts = Post::with('seen')
    ->get();

我想对此进行修改,如果我是用户 #24,则查询不应返回帖子 #2,因为我已经看过它。

我该怎么做?

【问题讨论】:

    标签: laravel laravel-5 eloquent laravel-5.2


    【解决方案1】:

    您应该在查询构建器中使用方法whereNotExists,如下所示:

    $posts = Post::whereNotExists(function ($query) {
        $query->select(DB::raw(1))
              ->from('posts_seen')
              ->whereRaw('posts_seen.user_id = posts.user_id');
    })
    ->get();
    

    请注意,我还假设您不再需要 seen 关系。如果我错了,您可以再次拨打with

    【讨论】:

      【解决方案2】:

      你可以这样做:
      首先选择user_id标识的用户看到的post ids

      $posts_seen = PostSeen::where('user_id',$user_id)->get()->lists('post_id');
      

      然后使用whereNotIn()方法选择$posts_seen中除post ids之外的所有帖子。

      whereNotIn 方法验证给定列的值不是 包含在给定数组中:

      Post::whereNotIn('id',$posts_seen)->get();
      

      【讨论】:

        【解决方案3】:

        可以使用whereDoesntHave

        使用 where 子句向查询添加关系计数/存在条件。

        $posts = Post::whereDoesntHave('seen', function($query) use ($request){
                    $query->where('user_id', $request->user()->id);
                })
        ->get();
        

        【讨论】:

          猜你喜欢
          • 2023-03-06
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多