在ReactiveMongo $in
查询中使用0.11
运算符时遇到问题。由于某种原因,查询返回零文档,但我可以确认ID存在。所以我假设我没有正确构建这个。
这是我的查询:
val query = BSONDocument("userId" -> userId, "convoId" -> BSONDocument("$in" -> BSONArray(convoIds)))
collection.find(query).cursor[ChatDesc](ReadPreference.primaryPreferred).collect[List]()
我通过应用列表构建我的BSONArray
:
BSONArray(List(id1, id2, ...))
以下是查询中使用的ID:
List(5594ee9f02fb36b06e2925b155ea043bfb006c5a6a8436be, 552c784430a54cf55e07190955ea043bfb006c5a6a8436be, 55af435c9524018461f750ec55ea043bfb006c5a6a8436be...)
如果我省略了$in
操作员并手动检查每个convoIds
字段,我可以确认55af435c9524018461f750ec55ea043bfb006c5a6a8436be
上方的第3个ID实际上在该集合中出现多次。此外,其他对象符合userId
字段的标准。
我唯一的另一个猜测是我需要在字段上创建某种MongoDB二级索引吗?
不知道我做错了什么。谢谢!
我把问题缩小到我如何应用BSONArray
。如果我手动粘贴这样的一个ID,BSONArray("thestringID")
,并运行查询它是成功的。看来奇怪,因为我认为List
是Traversable
的后代?
请指出您使用的版本。
如果您查看文档,可以看到BSONArray
可以从Traversable[BSONValue]
或Producer[BSONValue]
创建。
看来你的列表是List[String]
,这是Traversable
但不是Traversable[BSONValue]
,这意味着它尝试将前构造函数应用于Producer[BSONValue]*
。
实际上,Producer[BSONValue]
有类型类List[String]
的实例,因为只要元素类型也提供一个List
(String
就是这种情况)。这样的制作人自己创造了一个BSONArray
。
所以调用BSONArray(List("id1","id1"))
会产生BSONArray(BSONArray("id1","id2"))
,它有效,但对查询没有意义。
你不应该使用BSONArray for List,它足以将List放在BSONDocument中而不需要任何东西:
val query = BSONDocument("userId" -> userId, "convoId" -> BSONDocument("$in" -> convoIds))
或在Play JSON库中:
val query = Json.obj("convoId" -> Json.obj("$in" -> convoIds))
我不得不遍历列表,因为BSONArray
似乎不支持scala的本地List
。
var idFilter = BSONArray()
matchIds.foreach( id => idFilter = idFilter ++ id)
val query = BSONDocument("userId" -> userId, "convoId" -> BSONDocument("$in" -> idFilter))