[英]AppEngine Making ndb models json serializable
我们有一个ndb模型,我们想让json序列化。 这些模型非常简单:
class Pasta(ndb.Model):
name = ndb.StringProperty()
type = ndb.StringProperty()
comments = ndb.JsonProperty()
然后在处理程序方面,我们想做一些事情:
json.dumps(Pasta.query(Pasta.name=="Ravioli").fetch())
并将其返回给客户端,但它不断抛出json解析错误,因为类Pasta不是json可序列化的。 所以,问题是,我们必须实现__str__
或__repr__
还是有更__repr__
方法呢?
ndb.Model
实例具有to_dict()
函数: https : //developers.google.com/appengine/docs/python/ndb/modelclass#Model_to_dict
最简单的方法是:
json.dumps([p.to_dict() for p in Pasta.query(Pasta.name == "Ravioli").fetch()])
我不相信它已被记录,但对于现有的ext.db
模型,您可以使用db.to_dict()
(参见此处 )。
使用db.ReferenceProperty
和db.DateTimeProperty
要小心,因为当你调用json.dumps()
时它们会抛出错误。 快速解决方案是自定义JSONEncoder:
from datetime import datetime, date, time
from google.appengine.ext import db
import json
class JSONEncoder(json.JSONEncoder):
def default(self, o):
# If this is a key, you might want to grab the actual model.
if isinstance(o, db.Key):
o = db.get(o)
if isinstance(o, db.Model):
return db.to_dict(o)
elif isinstance(o, (datetime, date, time)):
return str(o) # Or whatever other date format you're OK with...
然后用这个编码:
JSONEncoder().encode(YourModel.all().fetch())
或者您可以像下面一样向模型添加计算属性:
class Taxes(ndb.Model):
name = ndb.StringProperty()
id = ndb.ComputedProperty(lambda self: self.key.id())
然后在你的get方法中只需调用to_dict,你就会获得id
rows = [row.to_dict() for row in Taxes.query()]
self.response.write(json.dumps(rows))
如果有一个ndb.KeyProperty引用不同的模型,你可以很好地覆盖字典方法,如下所示
def to_dict(self):
result = super(Point, self).to_dict()
result['x']=self.x.get().to_dict()
result['y']=self.y.get().to_dict()
return result
如果ndb.KeyProperty是一个列表(重复设置为True),请使用以下方法使用get_multi获取引用的模型
def to_dict(self):
result = super(Figure, self).to_dict()
result['points']=[p.to_dict() for p in ndb.get_multi(self.points)]
return result
如果有一个ndb.KeyProperty引用不同的模型,你可以很好地覆盖字典方法,如下所示
def to_dict(self):
result = super(Point, self).to_dict()
result['x']=self.x.get().to_dict()
result['y']=self.y.get().to_dict()
return result
如果ndb.KeyProperty是一个列表(重复设置为True),并且如果您打算序列化引用的模型,请使用以下方法使用get_multi获取引用的模型
def to_dict(self):
result = super(Figure, self).to_dict()
result['points']=[p.to_dict() for p in ndb.get_multi(self.points)]
return result
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.