GAE NDB 结构化列表转为 Json
我最近从ext.db切换到了新的NDB,但遇到了一些困难。
我想把一个结构化的列表转换成Json格式,这样我就可以发送给iPhone应用程序。但是我遇到了“不是JSON可序列化”的错误。我希望把用户喜欢的所有水果都转换成Json。如果一个用户喜欢苹果、橙子和草莓,那么在下面代码中的favorites
字段里应该包含这三种水果,以及它们的分数和评论。
我知道有to_dict和jsonProperty这两个东西,但我不知道怎么用。
以下是我现在的代码:
class FavFruits(ndb.Model):
fruit = ndb.StringProperty()
score = ndb.IntegerProperty()
comment = ndb.TextProperty()
class UserProfile(ndb.Model):
uid = ndb.StringProperty(required=True)
favFruits = ndb.StructuredProperty(FavFruits, repeated=True)
@classmethod
def makeJsonPackage(cls, uid):
fruitList = UserProfile.query(UserProfile.uid == uid).get()
entry = {}
entry["uid"] = fruitList.uid
entry["favorites"] = fruitList.favFruits
return (entry)
# down stream of the code
jsonData = UserProfile.makeJsonPackage(uid)
self.response.write(json.dumps(jsonData))
这个代码不行……问题出在entry["favorites"] = fruitList.favFruits
,因为我在把结构化列表转换成Json数据时遇到了问题。
我的目标是发送整个favFruits
的列表(多个水果)。我想保留结构化列表,因为当用户请求“苹果”时,我想查询数据,这样我就可以显示这个水果(苹果)及其相关的分数和评论。
任何帮助都将非常感谢。
1 个回答
根据 AppEngine 让 ndb 模型支持 JSON 序列化 和 文档,下面的代码应该可以正常工作。
这个方法会返回一个字典,里面包含模型的属性值。对于结构化属性(StructuredProperty)和本地结构化属性(LocalStructuredProperty),它们的值会被递归地转换成字典。
@classmethod
def makeJsonPackage(cls, uid):
fruitList = UserProfile.query(UserProfile.uid == uid).get()
return json.dumps(fruitList.to_dict())
更新1
userPorfile = UserProfile.query(UserProfile.uid == uid).get()
return json.dumps([k.to_dict() for k in userProfile.favFruits])
额外信息:使用 Endpoints
因为你想把 AppEngine 用作移动应用的后端 API 服务器,所以首先要看看 Endpoints API。这个 API 是专门为这种用途设计的。
https://developers.google.com/appengine/docs/java/endpoints/
基于 Endpoints,还有一个谷歌支持的包叫做 Endpoints Proto Datastore API。这个包提供了 ndb 模型和 Endpoints 之间更直接的连接。一开始可能会觉得有点难,但一旦你明白它是怎么工作的,就会发现它非常强大,可以节省很多时间。
http://endpoints-proto-datastore.appspot.com/
更新 2:
编辑1: 我为 ndb 模型写了一个 RESTFul API 生成器。
# generate restful api in one line
BigDataLab = EndpointRestBuilder(GPCode).build(
api_name="BigDataLab",
name="bigdatalab",
version="v1",
description="My Little Api"
)
代码库: https://github.com/Tagtoo/endpoints-proto-datastore-rest