在GAE存储字典列表
我有一个大约20个对象的列表,每个对象都有一个包含10个字典的列表。
我想把每个对象的这10个字典列表存储到GAE(谷歌应用引擎)上;但我觉得我写的代码可能不太对,无法正确存储这些信息到GAE。
这是我现在的代码:
class Tw(db.Model):
tags = db.ListProperty()
ip = db.StringProperty()
在我的主要请求处理器中,我有以下内容:
for city in lst_of_cities: # this is the list of 20 objects
dict_info = hw12.twitter(city) # this is the function to get the list of 10 dictionaries for each object in the list
datastore = Tw() # this is the class defined for db.model
datastore.tags.append(dict_info) #
datastore.ip = self.request.remote_addr
datastore.put()
data = Data.gql("") #data entities we need to fetch
我不确定这段代码是否正确。如果有人能帮忙就太好了,非常感谢。
3 个回答
4
自从这段话写成以来,App Engine推出了他们实验性的“ndb” Python数据库模型,里面特别有一个JsonProperty,这个功能基本上可以直接实现你想要的效果。
不过,你需要使用App Engine的Python 2.7版本,这个版本现在还不完全适合生产环境,但最近看起来挺稳定的。GvR本人似乎也在写很多代码,这对代码质量是个好兆头。我打算在今年的某个时候把它用在生产环境中……
4
欢迎来到Stack Overflow!
我发现了几个问题:
- 字典这种数据类型在App Engine的属性中是不能使用的。
- 你只保存了最后一个实体,之前的都被丢掉了。
- 你使用了一个列表属性,但你不是把字典中的每个元素都添加进去,而是一次性把整个列表添加上去。
因为你不能直接把字典存储在属性里,所以需要把它转换成其他格式,比如JSON或者pickle。下面是一个使用pickle的修改示例:
from google.appengine.ext import db
import pickle
class Tw(db.Model):
tags = db.BlobProperty()
ip = db.StringProperty()
entities = []
for city in lst_of_cities:
dict_info = hw12.twitter(city)
entity = Tw()
entity.tags = db.Blob(pickle.dumps(dict_info))
entity.ip = self.request.remote_addr
entities.append(entity)
db.put(entities)
当你稍后获取这个实体时,可以用pickle.loads(entity.tags)
来取出你的字典列表。
4
当我处理一些Google App Engine不直接支持的数据类型,比如字典或者自定义数据类型时,我通常会使用一个很方便的东西叫做 PickleProperty
。
from google.appengine.ext import db
import pickle
class PickleProperty(db.Property):
def get_value_for_datastore(self, model_instance):
value = getattr(model_instance, self.name, None)
return pickle.dumps(value)
def make_value_from_datastore(self, value):
return pickle.loads(value)
在你的 commons.py
模块中声明了 PickleProperty
类之后,你就可以用它来存储你的自定义数据,像这样:
from google.appengine.ext import db
from commons import PickleProperty
class Tw(db.Model):
tags = PickleProperty()
ip = db.StringProperty()
entities = []
for city in lst_of_cities:
dict_info = hw12.twitter(city)
entity = Tw()
entity.tags = dict_info
entity.ip = self.request.remote_addr
entities.append(entity)
db.put(entities)
要把数据取回来,可以这样做:
entity.tags