线程未返回所有订阅用户

Thread not returning all subscribed users

关于

我正在使用 Laravel 5.8 和 MySQL。我有一个线程 table 和线程详细信息 table。我正在从线程中获取所有记录,并且它与 threaddetails table 关联,只要在 threaddetails 中找到匹配的 user_id。

预计

它应该 return 我的所有线程和订阅用户都在该线程中。

当前

它 return 是我的所有线程,但从线程详细信息 table 它 return 仅是我的记录。它不会 return 与我聊天的其他订阅用户。

问题:

我是否遗漏了 获取数据的查询 部分?

Table:线程 - 架构

Schema::create('tblthread', function (Blueprint $table) {
    $table->unsignedMediumInteger('thread_id')->autoIncrement();
    $table->timestamp('created_on');
});

Table 线程示例数据

INSERT INTO tblthread (thread_id, created_on) VALUES
(1, '2019-08-07 20:30:54');

Table 话题详情

Schema::create('tblthreaddetails', function (Blueprint $table) {
    $table->unsignedMediumInteger('thread_detail_id')->autoIncrement();
    $table->unsignedMediumInteger('thread_id');
    $table->unsignedMediumInteger('user_id')->nullable();

    $table->foreign('thread_id')->references('thread_id')->on('tblthread')->onDelete('cascade');
});

示例数据 - 线程详细信息

INSERT INTO `tblthreaddetails` (`thread_detail_id`, `thread_id`, `user_id`) VALUES
(1, 1, 1),
(2, 1, 6);

查询以获取数据

ThreadModel::with(["Details" => function($query) use ($user_id) {
    $query->where("user_id", $user_id);
}])->get();

线程模型

class ThreadModel extends Model
{
    public $table = 'tblthread';
    public $primaryKey = 'thread_id';
    public $timestamps = false;

    public function Details() {
        return $this->hasMany("\ThreadDetailsModel", "thread_id", "thread_id");
    }
}

线程详细信息模型

class ThreadDetailsModel extends Model
{
    public $table = 'tblthreaddetails';
    public $primaryKey = 'thread_detail_id';
    public $timestamps = false;
}

tblthread 应该关联到一个用户。因此,您可以在其上定义 user_id 列。

查询应如下所示:

ThreadModel::where('user_id', $user_id)->with("Details")->get();
// So first you get all the threads that belong to you
// and then get all details for those threads (only)

希望对您有所帮助!

问题出在这里:

ThreadModel::with(["Details" => function($query) use ($user_id) {
    $query->where("user_id", $user_id);
}])->get();

此查询将过滤所有仅包含 user_id = $user_id 的相关 details。因此,当然,只会返回与 $user_id 相关的详细信息。所以,基本上你是在约束相关模型……而不是线程本身。因此,可能会返回一些没有与用户关联的任何详细信息的线程 $user_id 我假设您不想要...

试试这个:

  • 检查 Thread 是否至少有一个属于 user_id = $user_id 的关联 Detail
  • 加载 Thread 中的所有 Detail

所以这应该有效:

use Illuminate\Database\Eloquent\Builder;

// ...

public function myCoolMethod()
{
    $threads = ThreadModel
        ::has('details', function (Builder $query) use ($user_id) {
            $query->where('user_id', $user_id);
        })
        ->with('details')
        ->get();

    // ...
}

- 使用 has() 方法,我们正在检查 relationship existence。 - 使用 with() 方法,我们 eager loading 已选择 threads 的所有相关详细信息。

whereHas 解决了我的问题

ThreadModel
    ::whereHas('details', function (Builder $query) use ($user_id) {
        $query->where('user_id', $user_id);
    })
    ->with('details')
    ->get();