在Google App Engine的remote_api_shell.py中检索和编写实体时出错

时间:2012-12-17 00:45:08

标签: python google-app-engine app-engine-ndb

这是我的困境:我必须通过一个实体列表来检查是否有一些重复的属性 - 我使用的是NDB - 是空的。如果是,则为其分配值put()。否则我跳过实体。我正在尝试在谷歌应用引擎附带的远程登录shell中完成所有这些工作。

我试过迭代Model.query(),执行条件,并写入值,但是当我开始写入时,进程被挂起。当我最终Ctrl-C时,它弹出一个错误,说“assert response.set_status_size()== len(server_keys); AssertionError”。我假设这与它试图检索的实体的大小有关。谁知道怎么了?这是我目前的代码:

>>> for entity in Model.query():
...    if not len(entity.references):
...        entity.references = somevalue
...        continue
...    print 'skipped'

我只是过滤查询而不是使用if语句,但我不确定如何按重复属性的长度过滤查询。

3 个答案:

答案 0 :(得分:3)

你有多少个实体?如果你有超过100左右,从远程api查询是非常低效的(二次)。所以这可以解释它是挂起的。

你是对的,你不能写一个检测你正在寻找的条件的查询。

答案 1 :(得分:1)

代码示例在找到没有引用的第一个实体时返回(如果没有引用,则返回skipped)但是它可能会留下一些没有任何引用的实体。我不知道这是不是你想要的。

如果只有少数引用值可能,例如['python','ruby','php'],我认为你可以像Model.query(Model.references.IN(['python', 'ruby', 'php'])))一样进行Repeated Properties查询,区别对待该列表包含所有实体的列表,并迭代剩余的实体。 (我不太了解NDB,并且怀疑这将是一个很好的方法,但是期望它适用于某些数据集。)

答案 2 :(得分:1)

我终于搞定了!我使用query.fetch_page批量获取查询,然后迭代每个批处理并应用更改。

>>> more = True
>>> cursor = None
>>> while more:
...     batch, cursor, more = MyModel.query().fetch_page(50, start_cursor=cursor)
...     for entity in batch:
...          if not len(entity.references):
...               entity.references = somevalue
...               entity.put()
...     print "finished batch"