在Google App Engine中,调用put_async()需要get_result()吗?

14 投票
3 回答
1671 浏览
提问于 2025-04-16 17:58

随着GAE 1.5.0的新版本发布,我们现在有了一种简单的方法来进行异步的数据存储调用。请问在调用了put_async之后,我们是否需要调用get_result()?

举个例子,如果我有一个叫MyLogData的模型,我能否在我的处理程序返回之前直接调用:

put_async(MyLogData(text="My Text"))

而不调用相应的get_result()呢?GAE会在将结果发送给客户端之前自动等待任何未完成的调用吗?

需要注意的是,我并不太关心处理错误的情况。也就是说,我不介意这些存储操作中有些失败。

3 个回答

2

我也不太清楚,但这样做是有效的:

import datetime
from google.appengine.api import urlfetch

def main():
  rpc = urlfetch.create_rpc()
  urlfetch.make_fetch_call(rpc, "some://artificially/slow.url")
  print "Content-type: text/plain"
  print
  print str(datetime.datetime.now())

if __name__ == '__main__':
  main()

这个远程网址会先等待3秒钟,然后给我发一封邮件。App Engine的处理程序会立刻返回,而远程网址会按预期完成。因为这两个服务使用的是相同的底层RPC框架,所以我猜测数据存储的行为也差不多。

这是个好问题。不过,也许Nick或者其他谷歌的员工能给出明确的答案。

3

db.put_async 在部署后可以正常工作,即使不调用 get_result,这是一种“发出请求就不管了”的方式。但在本地环境下,它不会执行任何操作,直到你调用了 get_result。想了解更多,可以查看这个链接,还有这个链接提供了更多背景信息。

7

我觉得要确定 get_result() 是否必要,可能没有什么确凿的方法,除非GAE团队的人来确认。不过我觉得它可能不是必需的。下面是我测试的过程。

我写了一个简单的处理程序:

class DB_TempTestModel(db.Model):
    data = db.BlobProperty()

class MyHandler(webapp.RequestHandler):
    def get(self):
        starttime = datetime.datetime.now()
        lots_of_data = ' '*500000
        if self.request.get('a') == '1':
            db.put(DB_TempTestModel(data=lots_of_data))
            db.put(DB_TempTestModel(data=lots_of_data))
            db.put(DB_TempTestModel(data=lots_of_data))
            db.put(DB_TempTestModel(data=lots_of_data))
        if self.request.get('a') == '2':
            db.put_async(DB_TempTestModel(data=lots_of_data))
            db.put_async(DB_TempTestModel(data=lots_of_data))
            db.put_async(DB_TempTestModel(data=lots_of_data))
            db.put_async(DB_TempTestModel(data=lots_of_data))
        self.response.out.write(str(datetime.datetime.now()-starttime))

我在一个高复制应用上运行了很多次。

每次数据都能成功写入,这让我相信,除非数据存储那边出现故障(这种情况不太可能),数据应该会被写入。

有个有趣的地方是,当我用 put_async() 写入数据时(?a=2),处理请求的时间平均比用 put()?a=1)快大约2到3倍(这不是一个很科学的测试,只是我大致观察的结果)。

但是 cpu_msapi_cpu_ms 对于 ?a=1?a=2 是一样的。

从日志来看:

ms=440 cpu_ms=627 api_cpu_ms=580 cpm_usd=0.036244

对比

ms=149 cpu_ms=627 api_cpu_ms=580 cpm_usd=0.036244

在客户端,看请求的网络延迟时,结果也是一样的,也就是说 ?a=2 的请求至少快了2倍。对客户端来说绝对是个好消息……但在服务器端似乎没有什么好处。

有没有GAE团队的人愿意评论一下?

撰写回答