存在连接用户和汽车的mongo文档。它包含以下字段:
User.cars是嵌入式文档的数组。如果查询尚未包含ID为$ carId的Car
,则需要编写查询以仅将Car插入此字段以下查询将每次为$ userId和$ carId创建一条新记录。它应该做的是不插入新记录或更新驱动值。
$qb
->findAndUpdate()
->upsert(true)
->field('userId')->equals($userId)
->field('cars.id')->notEqual($carId)
->field('cars')->addToSet([
'id' => $carId,
'driven' => new \DateTime(),
])
->field('updated')->set(new \DateTime())
->field('created')->setOnInsert(new \DateTime())
->limit(1)
;
return $qb->getQuery()->execute();
从查询中删除notEqual($ carId)将始终将记录插入User.cars,这也是不可取的。
最终结果应该是User.cars只包含每个carId的一条记录。
答案 0 :(得分:0)
如果您以后不需要搜索cars
数组,则可以将其存储为对象,并使用$carId
作为关键字:
$qb
->findAndUpdate()
->upsert(true)
->field('userId')->equals($userId)
->field("cars.$carId")->set([
'id' => $carId,
'driven' => new \DateTime(),
])
->field('updated')->set(new \DateTime())
->field('created')->setOnInsert(new \DateTime())
->limit(1)
;
return $qb->getQuery()->execute();
如果cars
在文档中映射为EmbedMany
,您可能需要将collection's strategy更改为set
或atomicSet
(我建议后者)否则ODM会在每次保存时重新索引数组。
再一次,这个解决方案有其缺点,根据您希望如何使用您的数据,它可以被认为是严重的,但它解决了有问题的问题。
另外,->limit(1)
是多余的,因为->findAndUpdate()
正在进行查询运行findAndModify
命令,该命令本质上是针对单个文档运行的。