在Mongoengine中使用键作为值
我在Django中使用mongoengine来操作mongodb。
但是,mongoengine的字段(比如StringField)让我不得不按照我不想要的方式来构建数据结构。我的意思是,它非常严格,要求我在还不知道具体会用什么键名之前,就得先写好键名。例如……
假设我不知道将会把什么键名放入数据库……
> for(var i=0; i<10; i++){
... o = {};
... o[i.toString()] = i + 100;
... db.test.save(o)
... }
> db.test.find()
{ "_id" : ObjectId("4ed623aa45c8729573313811"), "0" : 100 }
{ "_id" : ObjectId("4ed623aa45c8729573313812"), "1" : 101 }
{ "_id" : ObjectId("4ed623aa45c8729573313813"), "2" : 102 }
{ "_id" : ObjectId("4ed623aa45c8729573313814"), "3" : 103 }
{ "_id" : ObjectId("4ed623aa45c8729573313815"), "4" : 104 }
{ "_id" : ObjectId("4ed623aa45c8729573313816"), "5" : 105 }
{ "_id" : ObjectId("4ed623aa45c8729573313817"), "6" : 106 }
{ "_id" : ObjectId("4ed623aa45c8729573313818"), "7" : 107 }
{ "_id" : ObjectId("4ed623aa45c8729573313819"), "8" : 108 }
{ "_id" : ObjectId("4ed623aa45c872957331381a"), "9" : 109 }
[补充]
正如你所看到的,键名之间差别很大……
假设“我事先不知道将会把什么键名放入文档中”。
正如dcrosta回复的那样……我在寻找一种方法,可以在使用mongoengine时不提前指定字段。
[/补充]
我该如何通过mongoengine做到这一点?请给我一个像这样的数据结构设计:
class Test(Document):
tag = StringField(db_field='xxxx')
[补充]
我不知道'xxxx'会是什么键名。
抱歉……我来自韩国,所以我的英语有点生疏。请分享一些你的知识。谢谢你阅读这篇内容。
[/补充]
1 个回答
2
你有没有考虑直接使用PyMongo,而不是Mongoengine?Mongoengine是用来为你的文档定义和验证结构的,它提供了很多工具和方便的功能。如果你的文档内容会有很大差异,我不太确定Mongoengine是否适合你。
不过,如果你的所有文档都有一些共同的字段,而每个文档又有一些特定的字段,你可以使用Mongoengine的DictField
。这样做的缺点是,字段的键不会是“顶层”的,比如:
class UserThings(Document):
# you can look this document up by username
username = StringField()
# you can store whatever you want here
things = DictField()
dcrosta_things = UserThings(username='dcrosta')
dcrosta_things.things['foo'] = 'bar'
dcrosta_things.things['bad'] = 'quack'
dcrosta_things.save()
这会在MongoDB文档中生成如下内容:
{ _id: ObjectId(...),
_types: ["UserThings"],
_cls: "UserThings",
username: "dcrosta",
things: {
foo: "bar",
baz: "quack"
}
}
补充:我还想提一下,Mongoengine的开发分支上正在进行“动态”文档的工作,也就是说,当保存模型时,Python文档实例上的属性会被保存。详细信息和历史可以查看https://github.com/hmarr/mongoengine/pull/112。