@@ -124,10 +124,10 @@ def __init__(self, port, host='127.0.0.1', loglevel=logging.WARNING):
124
124
self .port = self .socket .getsockname ()[1 ]
125
125
126
126
def _message_received_ (self , handler , msg ):
127
- self .message_received (self .handler_to_client (handler ), self , msg )
127
+ self .message_received (self .handler_to_client (handler ), self , msg . decode () )
128
128
129
129
def _ping_received_ (self , handler , msg ):
130
- handler .send_pong (msg )
130
+ handler .send_pong (msg . decode () )
131
131
132
132
def _pong_received_ (self , handler , msg ):
133
133
pass
@@ -172,6 +172,8 @@ def setup(self):
172
172
self .keep_alive = True
173
173
self .handshake_done = False
174
174
self .valid_client = False
175
+ self .fragment_opcode = 0
176
+ self .fragment_payload_buf = bytearray ()
175
177
176
178
def handle (self ):
177
179
while self .keep_alive :
@@ -214,34 +216,46 @@ def read_next_message(self):
214
216
logger .warn ("Client must always be masked." )
215
217
self .keep_alive = 0
216
218
return
217
- if opcode == OPCODE_CONTINUATION :
218
- logger .warn ("Continuation frames are not supported." )
219
- return
220
- elif opcode == OPCODE_BINARY :
219
+ if opcode == OPCODE_BINARY :
221
220
logger .warn ("Binary frames are not supported." )
222
221
return
223
- elif opcode == OPCODE_TEXT :
224
- opcode_handler = self .server ._message_received_
225
- elif opcode == OPCODE_PING :
226
- opcode_handler = self .server ._ping_received_
227
- elif opcode == OPCODE_PONG :
228
- opcode_handler = self .server ._pong_received_
229
- else :
230
- logger .warn ("Unknown opcode %#x." % opcode )
231
- self .keep_alive = 0
232
- return
233
222
234
223
if payload_length == 126 :
235
224
payload_length = struct .unpack (">H" , self .rfile .read (2 ))[0 ]
236
225
elif payload_length == 127 :
237
226
payload_length = struct .unpack (">Q" , self .rfile .read (8 ))[0 ]
238
227
239
228
masks = self .read_bytes (4 )
240
- message_bytes = bytearray ()
229
+ payload = bytearray ()
241
230
for message_byte in self .read_bytes (payload_length ):
242
- message_byte ^= masks [len (message_bytes ) % 4 ]
243
- message_bytes .append (message_byte )
244
- opcode_handler (self , message_bytes .decode ('utf8' ))
231
+ message_byte ^= masks [len (payload ) % 4 ]
232
+ payload .append (message_byte )
233
+
234
+ if fin and opcode != OPCODE_CONTINUATION : # simple msg
235
+ if opcode == OPCODE_PING :
236
+ self .server ._ping_received_ (self , payload )
237
+ elif opcode == OPCODE_PONG :
238
+ self .server ._pong_received_ (self , payload )
239
+ elif opcode == OPCODE_TEXT :
240
+ self .server ._message_received_ (self , payload )
241
+ return
242
+
243
+ if not fin and opcode : # fragment msg start
244
+ self .fragment_opcode = opcode
245
+ self .fragment_payload_buf = payload
246
+ return
247
+
248
+ # "not opcode" is the same as "opcode == OPCODE_CONTINUATION"
249
+ if not fin and not opcode : # fragment msg ing
250
+ self .fragment_payload_buf .extend (payload )
251
+ return
252
+
253
+ if fin and opcode == OPCODE_CONTINUATION : # fragment msg end
254
+ if self .fragment_opcode == OPCODE_TEXT :
255
+ self .server ._message_received_ (self , self .fragment_payload_buf + payload )
256
+ elif self .fragment_opcode == OPCODE_BINARY :
257
+ pass
258
+ return
245
259
246
260
def send_message (self , message ):
247
261
self .send_text (message )
0 commit comments