I'm playing with pykka's actor model, and found some funny behaviour. Here's a demo that
- Launches an actor
- Gets a proxy to it
- Sets one of its @properties
Here's the code:
import time
import pykka
from sys import version_info as python_version
if python_version > (3, 0):
from _thread import get_ident
else:
from thread import get_ident
startTime = time.time()
def debug(msg, prefix='MSG'):
msgProc = "%s (thread #%s @ t = %.2fs): %s" % (prefix,get_ident(), time.time() - startTime, msg)
print(msgProc)
def mainThread():
debug('Launching support actor...', prefix='MAIN')
supportRef = supportThread.start()
debug('Getting support proxy...', prefix='MAIN')
supportProxy = supportRef.proxy()
debug('Getting myVal obj...', prefix='MAIN')
obj = supportProxy.myVal
debug(obj, prefix='MAIN')
debug('Setting myVal obj...', prefix='MAIN')
supportProxy.myVal = 2
debug('Setting myVal obj...', prefix='MAIN')
supportProxy.myVal = 3
supportProxy.stop()
class supportThread(pykka.ThreadingActor):
def __init__(self):
super(supportThread, self).__init__()
self._myVal = 0
@property
def myVal(self):
debug("Getting value", prefix='SUPPORT')
return self._myVal
@myVal.setter
def myVal(self, value):
debug("Setting value: processing for 1s...", prefix='SUPPORT')
time.sleep(1)
debug("Setting value: done", prefix='SUPPORT')
self._myVal = value
mainThread()
The output looks like this:
MAIN (thread #16344 @ t = 0.00s): Launching support actor...
MAIN (thread #16344 @ t = 0.00s): Getting support proxy...
SUPPORT (thread #16344 @ t = 0.00s): Getting value
MAIN (thread #16344 @ t = 0.00s): Getting myVal obj...
MAIN (thread #16344 @ t = 0.00s): <pykka.threading.ThreadingFuture object at 0x0000000002998518>
MAIN (thread #16344 @ t = 0.00s): Setting myVal obj...
SUPPORT (thread #16248 @ t = 0.00s): Getting value
SUPPORT (thread #16248 @ t = 0.00s): Setting value: processing for 1s...
SUPPORT (thread #16248 @ t = 1.00s): Setting value: done
MAIN (thread #16344 @ t = 1.00s): Setting myVal obj...
SUPPORT (thread #16248 @ t = 1.01s): Setting value: processing for 1s...
SUPPORT (thread #16248 @ t = 2.01s): Setting value: done
[Finished in 2.3s]
I have a couple of questions here.
- Why does the getter
supportThread.myVal()
get called in the main thread's context when.proxy()
is called? - Why do the lines
supportProxy.myVal = <a new value>
result in the main thread waiting for the actor to complete?
This seems like a bug to me: I thought that the proxy should only block execution if .get()
is called on a ThreadingFuture. Or is this intended?