我是否需要在Google App Engine中使用线程同步工具?

时间:2012-12-25 09:27:08

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

我在app.yaml中使用带有threadsafe: true的Google App Engine 1.7.4上的Python 2.7运行时。

我有以下代码:

@ndb.tasklet
def fn_a(container):
    ''' access datastore and mutate container '''

@ndb.tasklet
def fn_b(container):
    ''' access datastore and mutate container '''

@ndb.toplevel
def parallel_fn():
    shared_container = set()

    yield fn_a(shared_container), fn_b(shared_container)

fn_a()fn_b()访问和变异shared_container并在parallel_fn()中调用。 shared_container是标准库set,因此不是线程安全的。

我应该在适当的shared_container标准库锁中包装threading的mutator / accessor方法吗?

根据我对App Engine的理解,尽管设置了threadsafe: true,但每个实例都是单线程的。因此,不需要使用threading锁定对象?

初步测试显示不需要锁定,只会增加额外开销和死锁。它似乎也不应该做以下

if object not in shared_container:
    yield any tasklet operation
    shared_container.add(object)

shared_container可能会在yield操作期间由另一个执行行更新,因为object not in shared_container语句可能无效。然而

if object not in shared_container:
    shared_container.add(object)
    yield any tasklet operation

绝对没问题。

1 个答案:

答案 0 :(得分:3)

您不需要添加锁定代码,因为tasklet不在单独的线程中运行。在tasklet docs.

中了解相关信息

如果设置threadsafe:true,GAE是多线程的。启动不同的线程来处理同一实例上的多个请求。通常这不是问题,因为您应该设计您的请求处理程序,以便能够在各种服务器实例上运行。

这并不适用于这个问题,但如果您真的测试线程问题,请小心。我不确定,但我认为在dev_appserver和生产GAE服务器上运行之间的线程行为是不同的,所以请确保在两者上进行测试。