我有一个Document列表,每个包含50个(这可能会有所不同)EmbeddedDocument。现在我想查询包含以某种模式开头的id的所有EmbeddedDocument(在所有Document中)。
class Container(Document):
list = EmbeddedDocumentListField(Data)
class Data(EmbeddedDocument):
id=StringField(required=True, primary_key=True)
现在查询(或类似于startwith)将在数据的“id”上。
答案 0 :(得分:3)
作为嵌入字段,您需要使用"double underscore" __
的嵌入式语法来表示与原始"dot notation"以及startswith
或字符串istartswith
修饰符:
Container.objects(list__id__startswith="AAA")
否则,如果您需要“真正的”正则表达式而不是允许的快捷方式,那么您可以将__raw__
修饰符与“原始”MongoDB语法查询一起使用:
Container.objects(__raw__={ "list.id": ,re.compile('^AAA', re.IGNORECASE) })
或者可能是"list._id"
,具体取决于如何告知字段名称为嵌入对象序列化。
无论哪种方式基本上都会将查询卸载到数据库,在数据库中它可以使用它的功能来确定匹配。
当然有一个基本的mongoengine
限制,没有办法简单地投影匹配的数组元素。这就是如何读取和实例化类数据的。
您可以使用.aggregate()
方法返回“原始python对象”作为已实现类的替代方法:
Container._get_collection().aggregate({
{ "$match": { "list.id": ,re.compile('^AAA', re.IGNORECASE) } },
{ "$unwind": "$list" },
{ "$match": { "list.id": ,re.compile('^AAA', re.IGNORECASE) } },
{ "$group": {
"_id": "$_id",
"list": { "$push": "$list" }
}}
])
因此不再定义相同的class
,但如果需要,也没有什么可以阻止你提供原始数据来实例化所需类的新对象。