如何在数据透视表 table 中搜索由两个用户拥有的行

How to search a pivot table for rows that are owned by two users

抱歉,如果这是一个愚蠢的问题,但我是 Laravel 的新手。

我有两个模型和一个枢轴 table:

用户

id | name | password

public function conversations(): ?BelongsToMany
{
  return $this->belongsToMany(Conversation::class)->withTimestamps();
}

对话

id

public function users(): ?BelongsToMany
{
  return $this->belongsToMany(User::class)->withTimestamps();
}

conversation_user

id | conversation_id | user_id

我创建了一个对话并像这样为用户分配同步:

$user->conversations()->syncWithoutDetaching($conversation);
$targetUser->conversations()->syncWithoutDetaching($conversation);

一个用户可以有多个会话,一个会话可以有多个用户。这很好,但是当我想与两个特定用户进行对话时,我不知道利用 ORM 查找他们各自所属的对话的最佳方式。

我目前正在使用下一个方法,它有效但感觉有更好的方法利用 ORM 做事:

/**
 * Get a conversation by a target user id.
 *
 * @param int $targetUserId
 * @return mixed
 */
public function getConversationByTargetUserId(int $targetUserId)
{
    // Get the current user.
    $user = Auth::guard()->user();

    // Check the user exists.
    if (!$user) {
        throw new HttpException(500);
    }

    /**
     * Get all pivot tables where the
     * user ID is from the current user.
     */
    $userConversationIdsArray = DB::table('conversation_user')->where('user_id', $user->id)->pluck('conversation_id');

    /**
     * Get all pivot tables where the user
     * id is equal to the target id, and is
     * also owned by the current user. Return
     * the first instance that we come across.
     */
    $targetConversation = DB::table('conversation_user')->where(['conversation_id' => $userConversationIdsArray, 'user_id' => $targetUserId])->first();

    /**
     * Return the conversation.
     */
    return Conversation::find($targetConversation->conversation_id);
}

感谢您的宝贵时间:)

您没有使用 Eloquent 有什么特别的原因吗?它可能会更容易。

可以这样做,因为您已经有了用户。

$user->conversations()->has('users.id', '=', $targetUserId)->first();

(我没有测试过这个解决方案,所以我不确定它是否 100% 有效)

此外,您的第一个查询中可能有错字。可能是复制粘贴错误可能是打字错误。只是确定一下。

$userConversationIdsArray = DB::table('conversation_user')->where('user_id', $user->id)->pluck('id'); <---- 'id' shouldn't that be 'conversation_id'?

感谢@Fjarlaegur,他们让我走上了正轨。以下方法有效:

/**
 * Get a conversation by a target user id.
 *
 * @param int $targetUserId
 * @return mixed
 */
public function getConversationByTargetUserId(int $targetUserId)
{
    // Get the current user.
    $user = Auth::guard()->user();

    // Check the user exists.
    if (!$user) {
        throw new HttpException(500);
    }

    return $user->conversations()->whereHas('users', function ($query) use ($targetUserId) {
        $query->where('users.id', $targetUserId);
    })->first();
}