This commit is contained in:
Maximilian Hils 2015-07-04 15:46:45 +02:00
parent 4c831992aa
commit 9960565359

View File

@ -128,15 +128,17 @@ class Script:
class ReplyProxy(object):
def __init__(self, original_reply):
self._ignore_calls = 1
self.lock = threading.Lock()
def __init__(self, original_reply, script_thread):
self.original_reply = original_reply
self.script_thread = script_thread
self._ignore_call = True
self.lock = threading.Lock()
def __call__(self, *args, **kwargs):
with self.lock:
if self._ignore_calls > 0:
self._ignore_calls -= 1
if self._ignore_call:
self.script_thread.start()
self._ignore_call = False
return
self.original_reply(*args, **kwargs)
@ -145,16 +147,19 @@ class ReplyProxy(object):
def _handle_concurrent_reply(fn, o, *args, **kwargs):
# Make first call to o.reply a no op
reply_proxy = ReplyProxy(o.reply)
o.reply = reply_proxy
# Make first call to o.reply a no op and start the script thread.
# We must not start the script thread before, as this may lead to a nasty race condition
# where the script thread replies a different response before the normal reply, which then gets swallowed.
def run():
fn(*args, **kwargs)
# If the script did not call .reply(), we have to do it now.
reply_proxy()
ScriptThread(target=run).start()
script_thread = ScriptThread(target=run)
reply_proxy = ReplyProxy(o.reply, script_thread)
o.reply = reply_proxy
class ScriptThread(threading.Thread):