From c80a2db6653a11a9026f8a00ca7302e373177df7 Mon Sep 17 00:00:00 2001 From: Joey Payne Date: Wed, 27 Jan 2016 15:32:52 -0700 Subject: [PATCH] Fixed multiple packets being sent at once causing a json error. --- socketIO_client/__init__.py | 31 +++++++++++++----------- socketIO_client/transports.py | 45 ++++++++++++++++++++++------------- 2 files changed, 46 insertions(+), 30 deletions(-) diff --git a/socketIO_client/__init__.py b/socketIO_client/__init__.py index aafb335..1946323 100644 --- a/socketIO_client/__init__.py +++ b/socketIO_client/__init__.py @@ -275,7 +275,7 @@ class SocketIO(object): def _process_packet(self, packet): code, packet_id, path, data = packet namespace = self.get_namespace(path or '') - delegate = self._get_delegate(code) + delegate = self._get_delegate(code, packet) delegate(packet, namespace._find_event_callback) def _stop_waiting(self, for_callbacks): @@ -395,19 +395,22 @@ class SocketIO(object): except KeyError: raise PacketError('unhandled namespace path (%s)' % path) - def _get_delegate(self, code): - return { - '0': self._on_disconnect, - '1': self._on_connect, - '2': self._on_heartbeat, - '3': self._on_message, - '4': self._on_json, - '5': self._on_event, - '6': self._on_ack, - '7': self._on_error, - '8': self._on_noop, - '': self._on_noop - }.get(code, self._on_noop) + def _get_delegate(self, code, packet): + try: + return { + '0': self._on_disconnect, + '1': self._on_connect, + '2': self._on_heartbeat, + '3': self._on_message, + '4': self._on_json, + '5': self._on_event, + '6': self._on_ack, + '7': self._on_error, + '8': self._on_noop, + '': self._on_noop + }[code] + except KeyError: + raise PacketError('unexpected code ({}): {}'.format([code], packet)) def _on_disconnect(self, packet, find_event_callback): find_event_callback('disconnect')() diff --git a/socketIO_client/transports.py b/socketIO_client/transports.py index 215c838..e479cd1 100644 --- a/socketIO_client/transports.py +++ b/socketIO_client/transports.py @@ -8,6 +8,7 @@ import socket import sys import time import websocket +import re from .exceptions import ConnectionError, TimeoutError from .symmetries import _get_text @@ -97,22 +98,34 @@ class _AbstractTransport(object): yield self._packets.pop(0) except IndexError: pass - for packet_text in self.recv(timeout=timeout): - self._log(logging.DEBUG, '[packet received] %s', packet_text) - try: - packet_parts = packet_text.split(':', 3) - except AttributeError: - self._log(logging.WARNING, '[packet error] %s', packet_text) - continue - code, packet_id, path, data = None, None, None, None - packet_count = len(packet_parts) - if 4 == packet_count: - code, packet_id, path, data = packet_parts - elif 3 == packet_count: - code, packet_id, path = packet_parts - elif 1 == packet_count: - code = packet_parts[0] - yield code, packet_id, path, data + for packet_texts in self.recv(timeout=timeout): + #remove packet separator + packet_texts = re.sub('^\xef\xbf\xbd\w+\xef\xbf\xbd', '', + packet_texts) + + packets = packet_texts.split('\xef\xbf\xbd')[::2] + + for packet_text in packets: + self._log(logging.DEBUG, '[packet received] %s', packet_text) + sep_count = packet_text.count('\xef\xbf\xbd')/2 + + try: + packet_parts = packet_text.split(':', 3) + except AttributeError: + self._log(logging.WARNING, '[packet error] %s', packet_text) + continue + code, packet_id, path, data = None, None, None, None + packet_count = len(packet_parts) + if 4 == packet_count: + code, packet_id, path, data = packet_parts + elif 3 == packet_count: + code, packet_id, path = packet_parts + elif 1 == packet_count: + code = packet_parts[0] + if code and len(code) > 1: + code = code[-1] + + yield code, packet_id, path, data def _enqueue_packet(self, packet): self._packets.append(packet)