如果我有一个Querybuilder示例,并应用如下内容:
$queryBuilder->addSelect("
CASE
WHEN c.modifyStamp > c.createStamp THEN 'draft'
ELSE 'published'
END AS state
");
然后,在使用getResult
时,我会得到这样的结果:
[
0 => [
0 => \App\Entity\Test instance,
'state' => 'draft'
],
1 => [
0 => \App\Entity\Test instance,
'state' => 'published'
]
]
这并不是真正理想的(但我知道这是预期的,默认情况下).到我的实体,我尝试添加这个:
private $state;
public function getState(): string
{
return $this->state;
}
public function setState(string $state)
{
$this->state = $state;
}
...希望hydrator可以看到一个正确名称的属性(或setter),就像任何其他属性一样填充它,然后只给予我一个普通的对象数组(纯),而不是数组数组(混合)。例如,如果你使用Symfony serializer,你可以轻松地将一个数据数组应用于一个属性与数组键同名的对象。getScalarResult
会将每条记录中的所有字段都打包在一起,但我不想在这里使用数组。我想要一个对象数组,就像一个普通的getResult
会给予我的那样,如果我没有使用上面的语句。
我想我可以循环遍历结果(当处于“混合”形式时)并直接调用setter,或者使用getScalarResult
并以某种方式手动水合,但这些选项看起来很笨拙。所以:
1.是否有一个内置的选项/config/hydrator/trick我错过了?或..
1.我可以/应该为这种情况创建一个自定义水合器吗?或者
1.我是否应该只是吸收它,循环数据,应用悬空的额外字段,并以预期的格式返回数据?
谢谢:)
编辑:使用PHP后搜索是不可行的,因为draft
字段(上面的例子)也需要成为一组搜索过滤器的一部分(通过一个也有分页的UI-所以所有这些都需要在DB中完成,而不是作为事后的PHP代码。
2条答案
按热度按时间cu6pst1q1#
您可以使用DoctrinepostLoad事件向实体添加“真实的”属性并按原样使用它
l7mqbcuq2#
1. MySQL(〉= 5.7)生成列
(我还没有测试过这个方法)
参见:https://www.doctrine-project.org/projects/doctrine-orm/en/2.14/reference/attributes-reference.html#column和:https://dev.mysql.com/doc/refman/5.7/en/create-table-generated-columns.html
2.自定义补水器
(Ugly但不需要MySQL支持)
我能找到的唯一能让它在PHP中工作的东西是一个“丑陋”的水化代码黑客,这个黑客被Doctrine的
ObjectHydrator
的一些内部约定弄得更丑陋。这个实体就像你拥有的一样:
我在控制器中使用了以下代码:
3.数据库视图
如果其他方法都失败了,你可以使用一个MySQL视图,让你的实体Map到它。这样,视图就做了
CASE WHEN
,从你的实体的Angular 来看,它只是另一个列。