Doctrine 查询生成器 - 无法生成具有非字符串列名的 IN
Doctrine query builder - where IN with non string column names can't be generated
因为这个我睡不着,我要么一定错过了一些非常明显的东西,要么不能那样做。
我有这个 Doctrine Query Builder 东西:
$this->queryBuilder
->where('entity.id != ' . $id)
->andWhere(
$this->queryBuilder->expr()->andX(
$this->queryBuilder->expr()->in(":validatedValue", ['slug', 'title', 'content'])
)
)
->setParameter('validatedValue', $value);
现在它产生这样的东西:
SELECT
p0_.id AS id_0,
p0_.title AS title_1,
p0_.teaser AS teaser_2,
p0_.content AS content_3,
p0_.slug AS slug_4
FROM
posts p0_
WHERE
p0_.id <> 1
AND 'my-string-value-something something' IN('slug', 'title', 'content')
我对这行有问题:
AND 'my-string-value-something something' IN('slug', 'title', 'content')
我希望能够检查实际的列,所以我必须生成如下内容:
AND 'my-string-value-something something' IN(slug, title, content)
您已经注意到我想要的正确版本,如果有意义的话,它没有在字段名称周围加上任何引号。如果它们在那里,它将被视为一个字符串,而不是 table.
中的实际列
我似乎无法使用此查询生成器生成它。我尝试了各种技巧和嵌套 expr()
,但我尝试过的都没有用。
有没有人知道我如何与建筑商合作?我可以用构建器来做,还是应该只使用 DQL 或纯 SQL?
就做我想做的事而言,我发现以一种想做的方式根本不可能。
我认为从外观上看,它总是将数组中的元素用引号引起来。我不认为它可以关闭。即使有一些聪明的不同方法来处理这个问题,对于这样一个简单的事情来说似乎也需要付出太多的努力。
/**
* Creates an IN() expression with the given arguments.
*
* @param string $x Field in string format to be restricted by IN() function.
* @param mixed $y Argument to be used in IN() function.
*
* @return Expr\Func
*/
public function in($x, $y)
{
if (is_array($y)) {
foreach ($y as &$literal) {
if ( ! ($literal instanceof Expr\Literal)) {
$literal = $this->_quoteLiteral($literal);
}
}
}
return new Expr\Func($x . ' IN', (array) $y);
}
这正是我从 Doctrine 中得到一堆不需要的引语的方式。
$literal = $this->_quoteLiteral($literal);
关于我如何解决我的问题,我完全按照@Bananaapple 在我 post 的评论中建议的那样做了。所以现在我的代码如下所示:
// build conditions to determine which fields should be checked for the value
foreach ($constraint->fields as $field) {
$fieldsConditions[] = $this->queryBuilder->expr()->eq('entity.' . $field, ':value');
}
// we should always have fields as this is taken care of before we even get to this point
if (!empty($fieldsConditions)) {
$this->queryBuilder->andWhere(
$this->queryBuilder->expr()->orX(...$fieldsConditions)
)->setParameter('value', $value);
}
我希望这会对某人有所帮助。
因为这个我睡不着,我要么一定错过了一些非常明显的东西,要么不能那样做。
我有这个 Doctrine Query Builder 东西:
$this->queryBuilder
->where('entity.id != ' . $id)
->andWhere(
$this->queryBuilder->expr()->andX(
$this->queryBuilder->expr()->in(":validatedValue", ['slug', 'title', 'content'])
)
)
->setParameter('validatedValue', $value);
现在它产生这样的东西:
SELECT
p0_.id AS id_0,
p0_.title AS title_1,
p0_.teaser AS teaser_2,
p0_.content AS content_3,
p0_.slug AS slug_4
FROM
posts p0_
WHERE
p0_.id <> 1
AND 'my-string-value-something something' IN('slug', 'title', 'content')
我对这行有问题:
AND 'my-string-value-something something' IN('slug', 'title', 'content')
我希望能够检查实际的列,所以我必须生成如下内容:
AND 'my-string-value-something something' IN(slug, title, content)
您已经注意到我想要的正确版本,如果有意义的话,它没有在字段名称周围加上任何引号。如果它们在那里,它将被视为一个字符串,而不是 table.
中的实际列我似乎无法使用此查询生成器生成它。我尝试了各种技巧和嵌套 expr()
,但我尝试过的都没有用。
有没有人知道我如何与建筑商合作?我可以用构建器来做,还是应该只使用 DQL 或纯 SQL?
就做我想做的事而言,我发现以一种想做的方式根本不可能。
我认为从外观上看,它总是将数组中的元素用引号引起来。我不认为它可以关闭。即使有一些聪明的不同方法来处理这个问题,对于这样一个简单的事情来说似乎也需要付出太多的努力。
/**
* Creates an IN() expression with the given arguments.
*
* @param string $x Field in string format to be restricted by IN() function.
* @param mixed $y Argument to be used in IN() function.
*
* @return Expr\Func
*/
public function in($x, $y)
{
if (is_array($y)) {
foreach ($y as &$literal) {
if ( ! ($literal instanceof Expr\Literal)) {
$literal = $this->_quoteLiteral($literal);
}
}
}
return new Expr\Func($x . ' IN', (array) $y);
}
这正是我从 Doctrine 中得到一堆不需要的引语的方式。
$literal = $this->_quoteLiteral($literal);
关于我如何解决我的问题,我完全按照@Bananaapple 在我 post 的评论中建议的那样做了。所以现在我的代码如下所示:
// build conditions to determine which fields should be checked for the value
foreach ($constraint->fields as $field) {
$fieldsConditions[] = $this->queryBuilder->expr()->eq('entity.' . $field, ':value');
}
// we should always have fields as this is taken care of before we even get to this point
if (!empty($fieldsConditions)) {
$this->queryBuilder->andWhere(
$this->queryBuilder->expr()->orX(...$fieldsConditions)
)->setParameter('value', $value);
}
我希望这会对某人有所帮助。