转换 MySQL 在 table 到 Eloquent 查询中搜索一对值
Convert MySQL search for a pair of values in a table to Eloquent query
我在使用 Eloquent
重现这种 MySQL 查询时遇到问题
SELECT *
FROM foo
WHERE (column1, column2) IN (('foo', 1), ('bar', 2))
Eloquent 查询生成器中有一个名为 whereIn()
的方法,但它只能接收一列作为参数:
/**
* Add a "where in" clause to the query.
*
* @param string $column
* @param mixed $values
* @param string $boolean
* @param bool $not
* @return $this
*/
public function whereIn($column, $values, $boolean = 'and', $not = false)
{
...
}
所以,你不能这样做
$qb = $this->model->whereIn(['column1', 'column2'], array([1, 2], [1,3], [3, 32]));
我目前正在努力寻找解决方案,但如果有人能提供帮助,我将不胜感激:)
编辑:
我设法这样做了:
/**
* ...
*/
public function findConnectionsByUser(User $user, array $userConnectionIds)
{
$qb = $this->model->query();
...
return $this->createQueryBuilderForUserConnectionsWithUserIds($qb, $user, $userConnectionIds)->get();
}
/**
* @param Builder $qb
* @param User $user
* @param array $userConnectionIds
*
* @return Builder
*/
private function createQueryBuilderForUserConnectionsWithUserIds(Builder $qb, User $user, array $userConnectionIds)
{
foreach ($userConnectionIds as $userConnectionId) {
$qb->orWhere(array(
array('receiver_id', $user->id),
array('initiator_id', $userConnectionId)
))
->orWhere([
['receiver_id', $userConnectionId],
['initiator_id', $user->id]
]);
}
return $qb;
}
编辑 2(更具可扩展性的解决方案):
$qb = $this->model->query();
$oneSide = $this->model->newQuery()->where('receiver_id', '=', $user->id)
->whereIn('initiator_id', $userConnectionsIds);
return $qb->where('initiator_id', '=', $user->id)
->whereIn('receiver_id', $userConnectionsIds)
->union($oneSide)->get();
这有点粗糙,但您可以将列连接成一列,用一些其他未使用的字符(如“|”)将两列分隔开。
您可以尝试像
那样嵌套它们
$qb = $this->model->whereIn('column1', [1, 2, 3])
->orWhere(function ($query) {
$query->whereIn('column2', [2, 3, 32]);
});
也不确定您是否可以像这样简单地使用 whereIn。先试试
$qb = $this->model->whereIn('column1', [1, 2, 3])
->whereIn('column2', [2, 3, 32]);
第一个查询读起来更像 OR
,第二个更像 AND
查询。
我在使用 Eloquent
重现这种 MySQL 查询时遇到问题SELECT *
FROM foo
WHERE (column1, column2) IN (('foo', 1), ('bar', 2))
Eloquent 查询生成器中有一个名为 whereIn()
的方法,但它只能接收一列作为参数:
/**
* Add a "where in" clause to the query.
*
* @param string $column
* @param mixed $values
* @param string $boolean
* @param bool $not
* @return $this
*/
public function whereIn($column, $values, $boolean = 'and', $not = false)
{
...
}
所以,你不能这样做
$qb = $this->model->whereIn(['column1', 'column2'], array([1, 2], [1,3], [3, 32]));
我目前正在努力寻找解决方案,但如果有人能提供帮助,我将不胜感激:)
编辑: 我设法这样做了:
/**
* ...
*/
public function findConnectionsByUser(User $user, array $userConnectionIds)
{
$qb = $this->model->query();
...
return $this->createQueryBuilderForUserConnectionsWithUserIds($qb, $user, $userConnectionIds)->get();
}
/**
* @param Builder $qb
* @param User $user
* @param array $userConnectionIds
*
* @return Builder
*/
private function createQueryBuilderForUserConnectionsWithUserIds(Builder $qb, User $user, array $userConnectionIds)
{
foreach ($userConnectionIds as $userConnectionId) {
$qb->orWhere(array(
array('receiver_id', $user->id),
array('initiator_id', $userConnectionId)
))
->orWhere([
['receiver_id', $userConnectionId],
['initiator_id', $user->id]
]);
}
return $qb;
}
编辑 2(更具可扩展性的解决方案):
$qb = $this->model->query();
$oneSide = $this->model->newQuery()->where('receiver_id', '=', $user->id)
->whereIn('initiator_id', $userConnectionsIds);
return $qb->where('initiator_id', '=', $user->id)
->whereIn('receiver_id', $userConnectionsIds)
->union($oneSide)->get();
这有点粗糙,但您可以将列连接成一列,用一些其他未使用的字符(如“|”)将两列分隔开。
您可以尝试像
那样嵌套它们$qb = $this->model->whereIn('column1', [1, 2, 3])
->orWhere(function ($query) {
$query->whereIn('column2', [2, 3, 32]);
});
也不确定您是否可以像这样简单地使用 whereIn。先试试
$qb = $this->model->whereIn('column1', [1, 2, 3])
->whereIn('column2', [2, 3, 32]);
第一个查询读起来更像 OR
,第二个更像 AND
查询。