Cakephp 3:在目标模型上使用条件进行反缓存
Cakephp 3: Countercache with conditions on the target model
我正在尝试计算与计划关联的点数,但仅限于计划续订日期之后下载的点数。希望这是有道理的。我会想象这样的事情,但它不起作用:
class SpotsTable extends Table
{
public function initialize(array $config)
{
$this->addBehavior('CounterCache', [
'Plan' => [
'creditsUsed' => [
'conditions' => [
'downloaded >' => 'Plan.renewed'
]
]
]
]);
...
}
...
}
现在基本上就像 Plan.renewed
意味着 NULL
一样。
这可能吗,还是我走错路了?
两个问题
1。标识符不能作为字符串值传递
当使用 key => value
格式时,值端将始终遵循 binding/escaping/casting 除非它是表达式对象,因此由于 downloaded
列可能是 date/time 类型,你最终会得到 Plan.renewed
被绑定为一个字符串,因此最终的 SQL 将类似于:
downloaded > 'Plan.renewed'
这可能总是导致错误。长话短说,使用例如标识符表达式:
'Spots.downloaded >' => new \Cake\Database\Expression\IdentifierExpression('Plan.renewed')
2。计数器查询无权访问关联的 table
Plan.renewed
不会在计数器缓存行为生成的查询中访问,它不会自动contain/join关联,它会创建一个基于外键值的带有条件的简单查询在当前处理的 Spot
个实体中。
因此您必须使用 custom/modified 查询,例如使用自定义查找器,如下所示:
'creditsUsed' => [
'finder' => 'downloadedAfterPlanRenewal'
]
// in SpotsTable
public function findDownloadedAfterPlanRenewal(\Cake\ORM\Query $query, array $options)
{
return $query
->innerJoinWith('Plan')
->where([
'Spots.downloaded >' => $query->identifier('Plan.renewed')
]);
}
这将正确加入关联,以便您可以与 Plan
中的字段进行比较。行为生成的原始主键条件将已应用于给定的查询对象。
另见
我正在尝试计算与计划关联的点数,但仅限于计划续订日期之后下载的点数。希望这是有道理的。我会想象这样的事情,但它不起作用:
class SpotsTable extends Table
{
public function initialize(array $config)
{
$this->addBehavior('CounterCache', [
'Plan' => [
'creditsUsed' => [
'conditions' => [
'downloaded >' => 'Plan.renewed'
]
]
]
]);
...
}
...
}
现在基本上就像 Plan.renewed
意味着 NULL
一样。
这可能吗,还是我走错路了?
两个问题
1。标识符不能作为字符串值传递
当使用 key => value
格式时,值端将始终遵循 binding/escaping/casting 除非它是表达式对象,因此由于 downloaded
列可能是 date/time 类型,你最终会得到 Plan.renewed
被绑定为一个字符串,因此最终的 SQL 将类似于:
downloaded > 'Plan.renewed'
这可能总是导致错误。长话短说,使用例如标识符表达式:
'Spots.downloaded >' => new \Cake\Database\Expression\IdentifierExpression('Plan.renewed')
2。计数器查询无权访问关联的 table
Plan.renewed
不会在计数器缓存行为生成的查询中访问,它不会自动contain/join关联,它会创建一个基于外键值的带有条件的简单查询在当前处理的 Spot
个实体中。
因此您必须使用 custom/modified 查询,例如使用自定义查找器,如下所示:
'creditsUsed' => [
'finder' => 'downloadedAfterPlanRenewal'
]
// in SpotsTable
public function findDownloadedAfterPlanRenewal(\Cake\ORM\Query $query, array $options)
{
return $query
->innerJoinWith('Plan')
->where([
'Spots.downloaded >' => $query->identifier('Plan.renewed')
]);
}
这将正确加入关联,以便您可以与 Plan
中的字段进行比较。行为生成的原始主键条件将已应用于给定的查询对象。