diff --git a/socketIO_client/__init__.py b/socketIO_client/__init__.py index d065bf2..c4962a5 100644 --- a/socketIO_client/__init__.py +++ b/socketIO_client/__init__.py @@ -1,115 +1,219 @@ -# !!! Get pong -# !!! Change print statements into logging statements - - import json import requests import time -__version__ = '0.5.4' +__version__ = '0.6.1' TRANSPORTS = [] class EngineIO(object): - _engine_io_protocol = 3 - _request_index = 0 + _engineIO_protocol = 3 + _engineIO_request_index = 0 def __init__( - self, host, port=None, - resource='engine.io'): + self, + host, port=None, Namespace=None, + wait_for_connection=True, transports=TRANSPORTS, + resource='engine.io', **kw): self._url = 'http://%s:%s/%s/' % (host, port, resource) self._session = requests.Session() + print self._url response = self._session.get(self._url, params={ - 'EIO': self._engine_io_protocol, + 'EIO': self._engineIO_protocol, 'transport': 'polling', 't': self._get_timestamp(), }) - packs = _decode_content(response.content) - packet_type, packet = packs[0] - assert packet_type == 0 - packet_json = json.loads(packet) - print packet_json - # packet_json['pingInterval'] - # packet_json['pingTimeout'] - # packet_json['upgrades'] - self._session_id = packet_json['sid'] + print response.url - response = self._session.get(self._url, params={ - 'EIO': self._engine_io_protocol, - 'transport': 'polling', - 't': self._get_timestamp(), - 'sid': self._session_id, - }) - packs = _decode_content(response.content) - for packet_type, packet in packs: - print 'engineIO_packet_type = %s' % packet_type - print 'socketIO_packet_type = %s' % packet[0] - print 'packet = %s' % packet[1:] + engineIO_packets = _decode_content(response.content) + print engineIO_packets + engineIO_packet_type, engineIO_packet_data = engineIO_packets[0] + assert engineIO_packet_type == 0 + engineIO_packet_json = json.loads(engineIO_packet_data) + print engineIO_packet_json + # engineIO_packet_json['pingInterval'] + # engineIO_packet_json['pingTimeout'] + # engineIO_packet_json['upgrades'] + self._session_id = engineIO_packet_json['sid'] + + def wait(self): + while True: + self._process_packets() + + def _process_packets(self): + for engineIO_packet in self._recv_packet(): + self._process_packet(engineIO_packet) + + def _process_packet(self, packet): + engineIO_packet_type, engineIO_packet_data = packet + print 'engineIO_packet_type = %s' % engineIO_packet_type + engineIO_packet_data_parsed = _parse_engineIO_data( + engineIO_packet_data) + # Launch callbacks + namespace = self.get_namespace() + delegate = { + 0: self._on_open, + 1: self._on_close, + 2: self._on_ping, + 3: self._on_pong, + 4: self._on_message, + 5: self._on_upgrade, + 6: self._on_noop, + }[engineIO_packet_type] + delegate(engineIO_packet_data_parsed, namespace._find_packet_callback) + return engineIO_packet_data + + def get_namespace(self): + pass + + def _on_open(self): + pass + + def _on_close(self): + pass + + def _on_ping(self): + pass + + def _on_pong(self): + pass + + def _on_message(self): + pass + + def _on_upgrade(self): + pass + + def _on_noop(self): + pass def _get_timestamp(self): - timestamp = '%s-%s' % (int(time.time() * 1000), self._request_index) - self._request_index += 1 + timestamp = '%s-%s' % ( + int(time.time() * 1000), self._engineIO_request_index) + self._engineIO_request_index += 1 return timestamp - def _message(self, packet): - packet_type = 4 + def _message(self, engineIO_packet_data): + engineIO_packet_type = 4 response = self._session.post(self._url, params={ - 'EIO': self._engine_io_protocol, + 'EIO': self._engineIO_protocol, 'transport': 'polling', 't': self._get_timestamp(), 'sid': self._session_id, - }, data=_encode_content([(packet_type, packet)]), headers={ + }, data=_encode_content([ + (engineIO_packet_type, engineIO_packet_data), + ]), headers={ 'content-type': 'application/octet-stream', }) - packs = _decode_content(response.content) - for packet_type, packet in packs: - print 'engineIO_packet_type = %s' % packet_type - print 'socketIO_packet_type = %s' % packet[0] - print 'packet = %s' % packet[1:] + engineIO_packets = _decode_content(response.content) + for engineIO_packet_type, engineIO_packet_data in engineIO_packets: + socketIO_packet_type = int(engineIO_packet_data[0]) + socketIO_packet_data = engineIO_packet_data[1:] + print 'engineIO_packet_type = %s' % engineIO_packet_type + print 'socketIO_packet_type = %s' % socketIO_packet_type + print 'socketIO_packet_data = %s' % socketIO_packet_data def _ping(self): - packet_type = 2 - packet = '' + engineIO_packet_type = 2 + engineIO_packet_data = '' response = self._session.post(self._url, params={ - 'EIO': self._engine_io_protocol, + 'EIO': self._engineIO_protocol, 'transport': 'polling', 't': self._get_timestamp(), 'sid': self._session_id, - }, data=_encode_content([(packet_type, packet)]), headers={ + }, data=_encode_content([ + (engineIO_packet_type, engineIO_packet_data), + ]), headers={ 'content-type': 'application/octet-stream', }) - packs = _decode_content(response.content) - for packet_type, packet in packs: - print 'engineIO_packet_type = %s' % packet_type - print 'socketIO_packet_type = %s' % packet[0] - print 'packet = %s' % packet[1:] + engineIO_packets = _decode_content(response.content) + for engineIO_packet_type, engineIO_packet_data in engineIO_packets: + socketIO_packet_type = int(engineIO_packet_data[0]) + socketIO_packet_data = engineIO_packet_data[1:] + print 'engineIO_packet_type = %s' % engineIO_packet_type + print 'socketIO_packet_type = %s' % socketIO_packet_type + print 'socketIO_packet_data = %s' % socketIO_packet_data + + def _recv_packet(self): + response = self._session.get(self._url, params={ + 'EIO': self._engineIO_protocol, + 'transport': 'polling', + 't': self._get_timestamp(), + 'sid': self._session_id, + }) + for engineIO_packet in _decode_content(response.content): + yield engineIO_packet class SocketIO(EngineIO): def __init__( - self, host, port=None, Namespace=None, + self, + host, port=None, Namespace=None, wait_for_connection=True, transports=TRANSPORTS, resource='socket.io', **kw): - super(SocketIO, self).__init__(host, port, resource) + super(SocketIO, self).__init__( + host, port, Namespace, + wait_for_connection, transports, + resource, **kw) - def define(self): - pass - - def wait(self): + def define(self, Namespace, path=''): pass def emit(self, event, *args, **kw): - packet_type = 2 - packet = json.dumps([event]) - self._message(str(packet_type) + packet) + socketIO_packet_type = 2 + socketIO_packet_data = json.dumps([event]) + self._message(str(socketIO_packet_type) + socketIO_packet_data) def on(self, event, callback): pass + def _process_packet(self, packet): + engineIO_packet_data = super(SocketIO, self)._process_packet(packet) + socketIO_packet_type = int(engineIO_packet_data[0]) + socketIO_packet_data = engineIO_packet_data[1:] + print 'socketIO_packet_type = %s' % socketIO_packet_type + socketIO_packet_data_parsed = _parse_socketIO_data( + socketIO_packet_data) + # Launch callbacks + namespace = self.get_namespace() + delegate = { + 0: self._on_connect, + 1: self._on_disconnect, + 2: self._on_event, + 3: self._on_ack, + 4: self._on_error, + 5: self._on_binary_event, + 6: self._on_binary_ack, + }[socketIO_packet_type] + delegate( + socketIO_packet_data_parsed, namespace._find_packet_callback) + return socketIO_packet_data + + def _on_connect(self): + pass + + def _on_disconnect(self): + pass + + def _on_event(self): + pass + + def _on_ack(self): + pass + + def _on_error(self): + pass + + def _on_binary_event(self): + pass + + def _on_binary_ack(self): + pass + class BaseNamespace(object): pass @@ -121,52 +225,54 @@ class LoggingNamespace(BaseNamespace): def _decode_content(content): print content - packs = [] - index = 0 + packets = [] + content_index = 0 content_length = len(content) - while index < content_length: + while content_index < content_length: try: - index, packet_length = _read_packet_length(content, index) + content_index, packet_length = _read_packet_length( + content, content_index) except IndexError: break - index, packet = _read_packet(content, index, packet_length) - packet_type = int(packet[0]) - packet_payload = packet[1:] - packs.append((packet_type, packet_payload)) - return packs + content_index, packet_string = _read_packet_string( + content, content_index, packet_length) + packet_type = int(packet_string[0]) + packet_data = packet_string[1:] + packets.append((packet_type, packet_data)) + return packets -def _encode_content(packs): +def _encode_content(packets): parts = [] - for packet_type, packet_payload in packs: - packet = str(packet_type) + str(packet_payload) - parts.append(_make_packet_header(packet) + packet) + for packet_type, packet_data in packets: + packet_string = str(packet_type) + str(packet_data) + parts.append(_make_packet_header(packet_string) + packet_string) return ''.join(parts) -def _read_packet_length(content, index): - while ord(content[index]) != 0: - index += 1 - index += 1 +def _read_packet_length(content, content_index): + while ord(content[content_index]) != 0: + content_index += 1 + content_index += 1 packet_length_string = '' - while ord(content[index]) != 255: - packet_length_string += str(ord(content[index])) - index += 1 - return index, int(packet_length_string) + while ord(content[content_index]) != 255: + packet_length_string += str(ord(content[content_index])) + content_index += 1 + return content_index, int(packet_length_string) -def _read_packet(content, index, packet_length): - while ord(content[index]) == 255: - index += 1 - packet = content[index:index + packet_length] - return index + packet_length, packet +def _read_packet_string(content, content_index, packet_length): + while ord(content[content_index]) == 255: + content_index += 1 + packet_string = content[content_index:content_index + packet_length] + return content_index + packet_length, packet_string -def _make_packet_header(packet): - length_string = str(len(packet)) +def _make_packet_header(packet_string): + length_string = str(len(packet_string)) header_digits = [0] - for index in xrange(len(length_string)): - header_digits.append(ord(length_string[index]) - 48) + for i in xrange(len(length_string)): + header_digits.append(ord(length_string[i]) - 48) header_digits.append(255) return ''.join(chr(x) for x in header_digits) diff --git a/socketIO_client/tests/proxy.js b/socketIO_client/tests/proxy.js index 178c752..f5fbfca 100644 --- a/socketIO_client/tests/proxy.js +++ b/socketIO_client/tests/proxy.js @@ -23,8 +23,11 @@ var server = require('http').createServer(function(req, res) { function print_body(header, body) { var text = String(body); console.log(header + text); + if (text.charCodeAt(0) != 0) return; for (var i = 0; i < text.length; i++) { - console.log('body[%s] = %s = %s', i, text[i], text.charCodeAt(i)); + var character_code = text.charCodeAt(i); + console.log('body[%s] = %s = %s', i, text[i], character_code); + if (character_code == 65533) break; } } server.listen(8000);