summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSergey Shepelev <temotor@gmail.com>2013-10-09 22:30:22 +0400
committerSergey Shepelev <temotor@gmail.com>2013-12-03 22:30:02 +0400
commit76c1fcf3e5587db5c831bd825c2ba4bdf46a28c7 (patch)
tree5c7182d54f4f059f046f0150448c5971dd63f83e
parentbe8ddd5a893655f8d898b952cdb342af04e827c9 (diff)
downloadeventlet-76c1fcf3e5587db5c831bd825c2ba4bdf46a28c7.tar.gz
coros: remove Actor which was deprecated in 2010-01
-rw-r--r--eventlet/coros.py94
-rw-r--r--tests/coros_test.py128
2 files changed, 0 insertions, 222 deletions
diff --git a/eventlet/coros.py b/eventlet/coros.py
index 5d3d82e..37205e3 100644
--- a/eventlet/coros.py
+++ b/eventlet/coros.py
@@ -305,97 +305,3 @@ def queue(max_size=None):
return Queue()
else:
return Channel(max_size)
-
-
-class Actor(object):
- """ A free-running coroutine that accepts and processes messages.
-
- Kind of the equivalent of an Erlang process, really. It processes
- a queue of messages in the order that they were sent. You must
- subclass this and implement your own version of :meth:`received`.
-
- The actor's reference count will never drop to zero while the
- coroutine exists; if you lose all references to the actor object
- it will never be freed.
- """
- def __init__(self, concurrency = 1):
- """ Constructs an Actor, kicking off a new coroutine to process the messages.
-
- The concurrency argument specifies how many messages the actor will try
- to process concurrently. If it is 1, the actor will process messages
- serially.
- """
- warnings.warn("We're phasing out the Actor class, so as to get rid of"
- "the coros module. If you use Actor, please speak up on "
- "eventletdev@lists.secondlife.com, and we'll come up with a "
- "transition plan. If no one speaks up, we'll remove Actor "
- "in a future release of Eventlet.",
- DeprecationWarning, stacklevel=2)
-
- self._mailbox = collections.deque()
- self._event = _event.Event()
- self._killer = eventlet.spawn(self.run_forever)
- from eventlet import greenpool
- self._pool = greenpool.GreenPool(concurrency)
-
- def run_forever(self):
- """ Loops forever, continually checking the mailbox. """
- while True:
- if not self._mailbox:
- self._event.wait()
- self._event = _event.Event()
- else:
- # leave the message in the mailbox until after it's
- # been processed so the event doesn't get triggered
- # while in the received method
- self._pool.spawn_n(
- self.received, self._mailbox[0])
- self._mailbox.popleft()
-
- def cast(self, message):
- """ Send a message to the actor.
-
- If the actor is busy, the message will be enqueued for later
- consumption. There is no return value.
-
- >>> a = Actor()
- >>> a.received = lambda msg: msg
- >>> a.cast("hello")
- """
- self._mailbox.append(message)
- # if this is the only message, the coro could be waiting
- if len(self._mailbox) == 1:
- self._event.send()
-
- def received(self, message):
- """ Called to process each incoming message.
-
- The default implementation just raises an exception, so
- replace it with something useful!
-
- >>> class Greeter(Actor):
- ... def received(self, (message, evt) ):
- ... print "received", message
- ... if evt: evt.send()
- ...
- >>> a = Greeter()
-
- This example uses Events to synchronize between the actor and the main
- coroutine in a predictable manner, but this kinda defeats the point of
- the :class:`Actor`, so don't do it in a real application.
-
- >>> from eventlet.event import Event
- >>> evt = Event()
- >>> a.cast( ("message 1", evt) )
- >>> evt.wait() # force it to run at this exact moment
- received message 1
- >>> evt.reset()
- >>> a.cast( ("message 2", None) )
- >>> a.cast( ("message 3", evt) )
- >>> evt.wait()
- received message 2
- received message 3
-
- >>> eventlet.kill(a._killer) # test cleanup
- """
- raise NotImplementedError()
diff --git a/tests/coros_test.py b/tests/coros_test.py
deleted file mode 100644
index eb6bca9..0000000
--- a/tests/coros_test.py
+++ /dev/null
@@ -1,128 +0,0 @@
-from unittest import main
-from tests import LimitedTestCase, silence_warnings
-import eventlet
-from eventlet import coros
-from eventlet import event
-from eventlet import greenthread
-
-class IncrActor(coros.Actor):
- def received(self, evt):
- self.value = getattr(self, 'value', 0) + 1
- if evt: evt.send()
-
-
-class TestActor(LimitedTestCase):
- mode = 'static'
-
- @silence_warnings
- def setUp(self):
- super(TestActor, self).setUp()
- self.actor = IncrActor()
-
- def tearDown(self):
- super(TestActor, self).tearDown()
- greenthread.kill(self.actor._killer)
-
- def test_cast(self):
- evt = event.Event()
- self.actor.cast(evt)
- evt.wait()
- evt.reset()
- self.assertEqual(self.actor.value, 1)
- self.actor.cast(evt)
- evt.wait()
- self.assertEqual(self.actor.value, 2)
-
- def test_cast_multi_1(self):
- # make sure that both messages make it in there
- evt = event.Event()
- evt1 = event.Event()
- self.actor.cast(evt)
- self.actor.cast(evt1)
- evt.wait()
- evt1.wait()
- self.assertEqual(self.actor.value, 2)
-
- def test_cast_multi_2(self):
- # the actor goes through a slightly different code path if it
- # is forced to enter its event loop prior to any cast()s
- eventlet.sleep(0)
- self.test_cast_multi_1()
-
- def test_sleeping_during_received(self):
- # ensure that even if the received method cooperatively
- # yields, eventually all messages are delivered
- msgs = []
- waiters = []
- def received( (message, evt) ):
- eventlet.sleep(0)
- msgs.append(message)
- evt.send()
- self.actor.received = received
-
- waiters.append(event.Event())
- self.actor.cast( (1, waiters[-1]))
- eventlet.sleep(0)
- waiters.append(event.Event())
- self.actor.cast( (2, waiters[-1]) )
- waiters.append(event.Event())
- self.actor.cast( (3, waiters[-1]) )
- eventlet.sleep(0)
- waiters.append(event.Event())
- self.actor.cast( (4, waiters[-1]) )
- waiters.append(event.Event())
- self.actor.cast( (5, waiters[-1]) )
- for evt in waiters:
- evt.wait()
- self.assertEqual(msgs, [1,2,3,4,5])
-
- def test_raising_received(self):
- msgs = []
- def received( (message, evt) ):
- evt.send()
- if message == 'fail':
- raise RuntimeError()
- else:
- msgs.append(message)
-
- self.actor.received = received
-
- evt = event.Event()
- self.actor.cast( ('fail', evt) )
- evt.wait()
- evt.reset()
- self.actor.cast( ('should_appear', evt) )
- evt.wait()
- self.assertEqual(['should_appear'], msgs)
-
- @silence_warnings
- def test_multiple(self):
- self.actor = IncrActor(concurrency=2)
- total = [0]
- def received( (func, ev, value) ):
- func()
- total[0] += value
- ev.send()
- self.actor.received = received
-
- def onemoment():
- eventlet.sleep(0.1)
-
- evt = event.Event()
- evt1 = event.Event()
-
- self.actor.cast( (onemoment, evt, 1) )
- self.actor.cast( (lambda: None, evt1, 2) )
-
- evt1.wait()
- self.assertEqual(total[0], 2)
- eventlet.sleep(0)
- self.assertEqual(self.actor._pool.free(), 1)
- evt.wait()
- self.assertEqual(total[0], 3)
- eventlet.sleep(0)
- self.assertEqual(self.actor._pool.free(), 2)
-
-
-if __name__ == '__main__':
- main()