Improve error handling
authorCory Johns <johnsca@gmail.com>
Tue, 7 Mar 2017 22:36:22 +0000 (16:36 -0600)
committerCory Johns <johnsca@gmail.com>
Tue, 7 Mar 2017 22:48:00 +0000 (16:48 -0600)
juju/client/connection.py
juju/utils.py
tests/unit/test_connection.py

index 82ec4fa..b9eb3bc 100644 (file)
@@ -84,14 +84,22 @@ class Connection:
         await self.ws.close()
 
     async def recv(self, request_id):
+        if not self.is_open:
+            raise websockets.exceptions.ConnectionClosed(0, 'websocket closed')
         return await self.messages.get(request_id)
 
     async def receiver(self):
         while self.is_open:
-            result = await self.ws.recv()
-            if result is not None:
-                result = json.loads(result)
-                await self.messages.put(result['request-id'], result)
+            try:
+                result = await self.ws.recv()
+                if result is not None:
+                    result = json.loads(result)
+                    await self.messages.put(result['request-id'], result)
+            except Exception as e:
+                await self.messages.put_all(e)
+                raise
+        await self.messages.put_all(websockets.exceptions.ConnectionClosed(
+            0, 'websocket closed'))
 
     async def rpc(self, msg, encoder=None):
         self.__request_id__ += 1
@@ -111,7 +119,7 @@ class Connection:
             # API Error Response
             raise JujuAPIError(result)
 
-        if not 'response' in result:
+        if 'response' not in result:
             # This may never happen
             return result
 
index 9f5d63d..f4db66e 100644 (file)
@@ -59,7 +59,13 @@ class IdQueue:
     async def get(self, id):
         value = await self._queues[id].get()
         del self._queues[id]
+        if isinstance(value, Exception):
+            raise value
         return value
 
     async def put(self, id, value):
         await self._queues[id].put(value)
+
+    async def put_all(self, value):
+        for queue in self._queues.values():
+            await queue.put(value)
index 354b363..5371fdb 100644 (file)
@@ -3,6 +3,8 @@ import mock
 import pytest
 from collections import deque
 
+from websockets.exceptions import ConnectionClosed
+
 from .. import base
 from juju.client.connection import Connection
 
@@ -17,6 +19,8 @@ class WebsocketMock:
         pass
 
     async def recv(self):
+        if not self.responses:
+            raise ConnectionClosed(0, 'no reason')
         return json.dumps(self.responses.popleft())
 
     async def close(self):