Skip to content

Commit

Permalink
Client: handle error responses with invalid json (Fixes miguelgrinber…
Browse files Browse the repository at this point in the history
  • Loading branch information
miguelgrinberg committed Oct 7, 2020
1 parent c0a1c28 commit f543839
Show file tree
Hide file tree
Showing 4 changed files with 42 additions and 2 deletions.
6 changes: 5 additions & 1 deletion engineio/asyncio_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -218,9 +218,13 @@ async def _connect_polling(self, url, headers, engineio_path):
'Connection refused by the server')
if r.status < 200 or r.status >= 300:
self._reset()
try:
arg = await r.json()
except aiohttp.ClientError:
arg = None
raise exceptions.ConnectionError(
'Unexpected status code {} in server response'.format(
r.status), await r.json())
r.status), arg)
try:
p = payload.Payload(encoded_payload=await r.read())
except ValueError:
Expand Down
7 changes: 6 additions & 1 deletion engineio/client.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
from base64 import b64encode
from json import JSONDecodeError
import logging
try:
import queue
Expand Down Expand Up @@ -300,9 +301,13 @@ def _connect_polling(self, url, headers, engineio_path):
'Connection refused by the server')
if r.status_code < 200 or r.status_code >= 300:
self._reset()
try:
arg = r.json()
except JSONDecodeError:
arg = None
raise exceptions.ConnectionError(
'Unexpected status code {} in server response'.format(
r.status_code), r.json())
r.status_code), arg)
try:
p = payload.Payload(encoded_payload=r.content)
except ValueError:
Expand Down
16 changes: 16 additions & 0 deletions tests/asyncio/test_asyncio_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -290,6 +290,22 @@ def test_polling_connection_404(self):
)
assert exc.args[1] == {'foo': 'bar'}

def test_polling_connection_404_no_json(self):
c = asyncio_client.AsyncClient()
c._send_request = AsyncMock()
c._send_request.mock.return_value.status = 404
c._send_request.mock.return_value.json = AsyncMock(
side_effect=aiohttp.ContentTypeError('foo', 'bar')
)
try:
_run(c.connect('http://foo'))
except exceptions.ConnectionError as exc:
assert len(exc.args) == 2
assert (
exc.args[0] == 'Unexpected status code 404 in server response'
)
assert exc.args[1] == None

def test_polling_connection_invalid_packet(self):
c = asyncio_client.AsyncClient()
c._send_request = AsyncMock()
Expand Down
15 changes: 15 additions & 0 deletions tests/common/test_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -325,6 +325,21 @@ def test_polling_connection_404(self, _send_request):
)
assert exc.args[1] == {'foo': 'bar'}

@mock.patch('engineio.client.Client._send_request')
def test_polling_connection_404_no_json(self, _send_request):
_send_request.return_value.status_code = 404
_send_request.return_value.json.side_effect = json.JSONDecodeError(
'error', '<html></html>', 0)
c = client.Client()
try:
c.connect('http://foo')
except exceptions.ConnectionError as exc:
assert len(exc.args) == 2
assert (
exc.args[0] == 'Unexpected status code 404 in server response'
)
assert exc.args[1] is None

@mock.patch('engineio.client.Client._send_request')
def test_polling_connection_invalid_packet(self, _send_request):
_send_request.return_value.status_code = 200
Expand Down

0 comments on commit f543839

Please sign in to comment.