From 53550e907080cafb58d5af19d209e89971aaa79e Mon Sep 17 00:00:00 2001 From: meejah Date: Thu, 3 Nov 2016 23:27:30 -0600 Subject: [PATCH 1/6] test-requirements for asyncio --- setup.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/setup.py b/setup.py index 715089cb..b5a323b9 100644 --- a/setup.py +++ b/setup.py @@ -130,12 +130,13 @@ extras_require_dev = [ 'pyenchant>=1.6.6', # LGPL 'sphinxcontrib-spelling>=2.1.2', # BSD 'sphinx_rtd_theme>=0.1.9', # BSD + 'pytest_asyncio', ] # for testing by users with "python setup.py test" (not Tox, which we use) test_requirements = [ "pytest>=2.8.6", # MIT license - "mock>=1.3.0" # BSD license + "mock>=1.3.0", # BSD license ] From bb399d2891b74f1502e0b5307daf7544c41fee35 Mon Sep 17 00:00:00 2001 From: meejah Date: Thu, 3 Nov 2016 23:28:51 -0600 Subject: [PATCH 2/6] default protocol, why does this work without it? --- autobahn/asyncio/websocket.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/autobahn/asyncio/websocket.py b/autobahn/asyncio/websocket.py index 2267c4eb..0d798d14 100644 --- a/autobahn/asyncio/websocket.py +++ b/autobahn/asyncio/websocket.py @@ -239,6 +239,8 @@ class WebSocketServerFactory(WebSocketAdapterFactory, protocol.WebSocketServerFa Base class for asyncio-based WebSocket server factories. """ + protocol = WebSocketServerProtocol + def __init__(self, *args, **kwargs): """ In addition to all arguments to the constructor of From 5f3557533ca22134f153aae61dc0ae5167168283 Mon Sep 17 00:00:00 2001 From: meejah Date: Thu, 3 Nov 2016 23:30:51 -0600 Subject: [PATCH 3/6] a failing test-case --- .../asyncio/test/test_asyncio_websocket.py | 30 +++++++++++++++++++ 1 file changed, 30 insertions(+) create mode 100644 autobahn/asyncio/test/test_asyncio_websocket.py diff --git a/autobahn/asyncio/test/test_asyncio_websocket.py b/autobahn/asyncio/test/test_asyncio_websocket.py new file mode 100644 index 00000000..ff0c5ab8 --- /dev/null +++ b/autobahn/asyncio/test/test_asyncio_websocket.py @@ -0,0 +1,30 @@ +import pytest +import os + +# because py.test tries to collect it as a test-case +from asyncio.test_utils import TestLoop as AsyncioTestLoop +from unittest import TestCase +try: + from unittest.mock import Mock +except ImportError: + from mock import Mock +from autobahn.asyncio.websocket import WebSocketServerFactory + + +@pytest.mark.usefixtures("event_loop") # ensure we have pytest_asyncio installed +@pytest.mark.skipif(os.environ.get('USE_ASYNCIO', False), reason="Only for asyncio") +class Test(TestCase): + + @pytest.mark.asyncio(forbid_global_loop=True) + def test_websocket_custom_loop(self): + + def time_gen(): + yield + yield + + loop = AsyncioTestLoop(time_gen) + factory = WebSocketServerFactory(loop=loop) + server = factory() + transport = Mock() + + server.connection_made(transport) From 550b1e5694696634fd756c5054b9c970f77126ea Mon Sep 17 00:00:00 2001 From: meejah Date: Thu, 3 Nov 2016 23:31:00 -0600 Subject: [PATCH 4/6] Ensure we explicitly pass a loop to Future (if provided) --- autobahn/asyncio/websocket.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/autobahn/asyncio/websocket.py b/autobahn/asyncio/websocket.py index 0d798d14..90b45af5 100644 --- a/autobahn/asyncio/websocket.py +++ b/autobahn/asyncio/websocket.py @@ -100,7 +100,7 @@ class WebSocketAdapterProtocol(asyncio.Protocol): self.transport = None def _consume(self): - self.waiter = Future() + self.waiter = Future(loop=self.factory.loop or txaio.config.loop) def process(_): while len(self.receive_queue): From aa240cf4f8905a937df895deed3c083e77f76feb Mon Sep 17 00:00:00 2001 From: meejah Date: Thu, 3 Nov 2016 23:39:23 -0600 Subject: [PATCH 5/6] make RawSocket use txaio's loop (if configured) --- autobahn/asyncio/rawsocket.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/autobahn/asyncio/rawsocket.py b/autobahn/asyncio/rawsocket.py index 7d52e980..0e672944 100644 --- a/autobahn/asyncio/rawsocket.py +++ b/autobahn/asyncio/rawsocket.py @@ -69,14 +69,14 @@ class PrefixProtocol(asyncio.Protocol): self.log.debug('RawSocker Asyncio: Connection made with peer {peer}', peer=self.peer) self._buffer = b'' self._header = None - self._wait_closed = asyncio.Future() + self._wait_closed = txaio.create_future() @property def is_closed(self): if hasattr(self, '_wait_closed'): return self._wait_closed else: - f = asyncio.Future() + f = txaio.create_future() f.set_result(True) return f From 778dccefacee86250fe132717b658914f9e342b3 Mon Sep 17 00:00:00 2001 From: meejah Date: Fri, 4 Nov 2016 00:02:15 -0600 Subject: [PATCH 6/6] import from trollius properly --- autobahn/asyncio/test/test_asyncio_websocket.py | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/autobahn/asyncio/test/test_asyncio_websocket.py b/autobahn/asyncio/test/test_asyncio_websocket.py index ff0c5ab8..a752d3bb 100644 --- a/autobahn/asyncio/test/test_asyncio_websocket.py +++ b/autobahn/asyncio/test/test_asyncio_websocket.py @@ -2,13 +2,17 @@ import pytest import os # because py.test tries to collect it as a test-case -from asyncio.test_utils import TestLoop as AsyncioTestLoop -from unittest import TestCase +try: + from asyncio.test_utils import TestLoop as AsyncioTestLoop +except ImportError: + from trollius.test_utils import TestLoop as AsyncioTestLoop try: from unittest.mock import Mock except ImportError: from mock import Mock + from autobahn.asyncio.websocket import WebSocketServerFactory +from unittest import TestCase @pytest.mark.usefixtures("event_loop") # ensure we have pytest_asyncio installed