1import time 2import struct 3import unittest 4from unit.applications.lang.node import TestApplicationNode 5from unit.applications.websockets import TestApplicationWebsocket 6 7 8class TestNodeWebsockets(TestApplicationNode): 9 prerequisites = ['node'] 10 11 ws = TestApplicationWebsocket() 12 13 def setUp(self): 14 super().setUp() 15 16 self.assertIn( 17 'success', 18 self.conf( 19 {'http': {'websocket': {'keepalive_interval': 0}}}, 'settings' 20 ), 21 'clear keepalive_interval', 22 ) 23 24 self.skip_alerts.extend( 25 [r'last message send failed', r'socket close\(\d+\) failed'] 26 ) 27 28 def close_connection(self, sock): 29 self.assertEqual(self.recvall(sock, read_timeout=1), b'', 'empty sock') 30 31 self.ws.frame_write(sock, self.ws.OP_CLOSE, self.ws.serialize_close()) 32 33 self.check_close(sock) 34 35 def check_close(self, sock, code=1000, no_close=False): 36 frame = self.ws.frame_read(sock) 37 38 self.assertEqual(frame['fin'], True, 'close fin') 39 self.assertEqual(frame['opcode'], self.ws.OP_CLOSE, 'close opcode') 40 self.assertEqual(frame['code'], code, 'close code') 41 42 if not no_close: 43 sock.close() 44 45 def check_frame(self, frame, fin, opcode, payload, decode=True): 46 if opcode == self.ws.OP_BINARY or not decode: 47 data = frame['data'] 48 else: 49 data = frame['data'].decode('utf-8') 50 51 self.assertEqual(frame['fin'], fin, 'fin') 52 self.assertEqual(frame['opcode'], opcode, 'opcode') 53 self.assertEqual(data, payload, 'payload') 54 55 def test_node_websockets_handshake(self): 56 self.load('websockets/mirror') 57 58 resp, sock, key = self.ws.upgrade() 59 sock.close() 60 61 self.assertEqual(resp['status'], 101, 'status') 62 self.assertEqual(resp['headers']['Upgrade'], 'websocket', 'upgrade') 63 self.assertEqual( 64 resp['headers']['Connection'], 'Upgrade', 'connection' 65 ) 66 self.assertEqual( 67 resp['headers']['Sec-WebSocket-Accept'], self.ws.accept(key), 'key' 68 ) 69 70 def test_node_websockets_mirror(self): 71 self.load('websockets/mirror') 72 73 message = 'blah' 74 75 _, sock, _ = self.ws.upgrade() 76 77 self.ws.frame_write(sock, self.ws.OP_TEXT, message) 78 frame = self.ws.frame_read(sock) 79 80 self.assertEqual(message, frame['data'].decode('utf-8'), 'mirror') 81 82 self.ws.frame_write(sock, self.ws.OP_TEXT, message) 83 frame = self.ws.frame_read(sock) 84 85 self.assertEqual(message, frame['data'].decode('utf-8'), 'mirror 2') 86 87 sock.close() 88 89 def test_node_websockets_no_mask(self): 90 self.load('websockets/mirror') 91 92 message = 'blah' 93 94 _, sock, _ = self.ws.upgrade() 95 96 self.ws.frame_write(sock, self.ws.OP_TEXT, message, mask=False) 97 98 frame = self.ws.frame_read(sock) 99 100 self.assertEqual(frame['opcode'], self.ws.OP_CLOSE, 'no mask opcode') 101 self.assertEqual(frame['code'], 1002, 'no mask close code') 102 103 sock.close() 104 105 def test_node_websockets_fragmentation(self): 106 self.load('websockets/mirror') 107 108 message = 'blah' 109 110 _, sock, _ = self.ws.upgrade() 111 112 self.ws.frame_write(sock, self.ws.OP_TEXT, message, fin=False) 113 self.ws.frame_write(sock, self.ws.OP_CONT, ' ', fin=False) 114 self.ws.frame_write(sock, self.ws.OP_CONT, message) 115 116 frame = self.ws.frame_read(sock) 117 118 self.assertEqual( 119 message + ' ' + message, 120 frame['data'].decode('utf-8'), 121 'mirror framing', 122 ) 123 124 sock.close() 125 126 def test_node_websockets_frame_fragmentation_invalid(self): 127 self.load('websockets/mirror') 128 129 message = 'blah' 130 131 _, sock, _ = self.ws.upgrade() 132 133 self.ws.frame_write(sock, self.ws.OP_PING, message, fin=False) 134 135 frame = self.ws.frame_read(sock) 136 137 frame.pop('data') 138 self.assertDictEqual( 139 frame, 140 { 141 'fin': True, 142 'rsv1': False, 143 'rsv2': False, 144 'rsv3': False, 145 'opcode': self.ws.OP_CLOSE, 146 'mask': 0, 147 'code': 1002, 148 'reason': 'Fragmented control frame', 149 }, 150 'close frame', 151 ) 152 153 sock.close() 154 155 def test_node_websockets_large(self): 156 self.load('websockets/mirror_fragmentation') 157 158 message = '0123456789' * 3000 159 160 _, sock, _ = self.ws.upgrade() 161 162 self.ws.frame_write(sock, self.ws.OP_TEXT, message) 163 164 frame = self.ws.frame_read(sock) 165 data = frame['data'].decode('utf-8') 166 167 frame = self.ws.frame_read(sock) 168 data += frame['data'].decode('utf-8') 169 170 self.assertEqual(message, data, 'large') 171 172 sock.close() 173 174 def test_node_websockets_two_clients(self): 175 self.load('websockets/mirror') 176 177 message1 = 'blah1' 178 message2 = 'blah2' 179 180 _, sock1, _ = self.ws.upgrade() 181 _, sock2, _ = self.ws.upgrade() 182 183 self.ws.frame_write(sock1, self.ws.OP_TEXT, message1) 184 self.ws.frame_write(sock2, self.ws.OP_TEXT, message2) 185 186 frame1 = self.ws.frame_read(sock1) 187 frame2 = self.ws.frame_read(sock2) 188 189 self.assertEqual(message1, frame1['data'].decode('utf-8'), 'client 1') 190 self.assertEqual(message2, frame2['data'].decode('utf-8'), 'client 2') 191 192 sock1.close() 193 sock2.close() 194 195 @unittest.skip('not yet') 196 def test_node_websockets_handshake_upgrade_absent( 197 self 198 ): # FAIL https://tools.ietf.org/html/rfc6455#section-4.2.1 199 self.load('websockets/mirror') 200 201 key = self.ws.key() 202 resp = self.get( 203 headers={ 204 'Host': 'localhost', 205 'Connection': 'Upgrade', 206 'Sec-WebSocket-Key': key, 207 'Sec-WebSocket-Protocol': 'chat', 208 'Sec-WebSocket-Version': 13, 209 }, 210 read_timeout=1, 211 ) 212 213 self.assertEqual(resp['status'], 400, 'upgrade absent') 214 215 def test_node_websockets_handshake_case_insensitive(self): 216 self.load('websockets/mirror') 217 218 key = self.ws.key() 219 resp = self.get( 220 headers={ 221 'Host': 'localhost', 222 'Upgrade': 'WEBSOCKET', 223 'Connection': 'UPGRADE', 224 'Sec-WebSocket-Key': key, 225 'Sec-WebSocket-Protocol': 'chat', 226 'Sec-WebSocket-Version': 13, 227 }, 228 read_timeout=1, 229 ) 230 231 self.assertEqual(resp['status'], 101, 'status') 232 233 @unittest.skip('not yet') 234 def test_node_websockets_handshake_connection_absent(self): # FAIL 235 self.load('websockets/mirror') 236 237 key = self.ws.key() 238 resp = self.get( 239 headers={ 240 'Host': 'localhost', 241 'Upgrade': 'websocket', 242 'Sec-WebSocket-Key': key, 243 'Sec-WebSocket-Protocol': 'chat', 244 'Sec-WebSocket-Version': 13, 245 }, 246 read_timeout=1, 247 ) 248 249 self.assertEqual(resp['status'], 400, 'status') 250 251 def test_node_websockets_handshake_version_absent(self): 252 self.load('websockets/mirror') 253 254 key = self.ws.key() 255 resp = self.get( 256 headers={ 257 'Host': 'localhost', 258 'Upgrade': 'websocket', 259 'Connection': 'Upgrade', 260 'Sec-WebSocket-Key': key, 261 'Sec-WebSocket-Protocol': 'chat', 262 }, 263 read_timeout=1, 264 ) 265 266 self.assertEqual(resp['status'], 426, 'status') 267 268 @unittest.skip('not yet') 269 def test_node_websockets_handshake_key_invalid(self): 270 self.load('websockets/mirror') 271 272 resp = self.get( 273 headers={ 274 'Host': 'localhost', 275 'Upgrade': 'websocket', 276 'Connection': 'Upgrade', 277 'Sec-WebSocket-Key': '!', 278 'Sec-WebSocket-Protocol': 'chat', 279 'Sec-WebSocket-Version': 13, 280 }, 281 read_timeout=1, 282 ) 283 284 self.assertEqual(resp['status'], 400, 'key length') 285 286 key = self.ws.key() 287 resp = self.get( 288 headers={ 289 'Host': 'localhost', 290 'Upgrade': 'websocket', 291 'Connection': 'Upgrade', 292 'Sec-WebSocket-Key': [key, key], 293 'Sec-WebSocket-Protocol': 'chat', 294 'Sec-WebSocket-Version': 13, 295 }, 296 read_timeout=1, 297 ) 298 299 self.assertEqual( 300 resp['status'], 400, 'key double' 301 ) # FAIL https://tools.ietf.org/html/rfc6455#section-11.3.1 302 303 def test_node_websockets_handshake_method_invalid(self): 304 self.load('websockets/mirror') 305 306 key = self.ws.key() 307 resp = self.post( 308 headers={ 309 'Host': 'localhost', 310 'Upgrade': 'websocket', 311 'Connection': 'Upgrade', 312 'Sec-WebSocket-Key': key, 313 'Sec-WebSocket-Protocol': 'chat', 314 'Sec-WebSocket-Version': 13, 315 }, 316 read_timeout=1, 317 ) 318 319 self.assertEqual(resp['status'], 400, 'status') 320 321 def test_node_websockets_handshake_http_10(self): 322 self.load('websockets/mirror') 323 324 key = self.ws.key() 325 resp = self.get( 326 headers={ 327 'Host': 'localhost', 328 'Upgrade': 'websocket', 329 'Connection': 'Upgrade', 330 'Sec-WebSocket-Key': key, 331 'Sec-WebSocket-Protocol': 'chat', 332 'Sec-WebSocket-Version': 13, 333 }, 334 http_10=True, 335 read_timeout=1, 336 ) 337 338 self.assertEqual(resp['status'], 400, 'status') 339 340 def test_node_websockets_handshake_uri_invalid(self): 341 self.load('websockets/mirror') 342 343 key = self.ws.key() 344 resp = self.get( 345 headers={ 346 'Host': 'localhost', 347 'Upgrade': 'websocket', 348 'Connection': 'Upgrade', 349 'Sec-WebSocket-Key': key, 350 'Sec-WebSocket-Protocol': 'chat', 351 'Sec-WebSocket-Version': 13, 352 }, 353 url='!', 354 read_timeout=1, 355 ) 356 357 self.assertEqual(resp['status'], 400, 'status') 358 359 def test_node_websockets_protocol_absent(self): 360 self.load('websockets/mirror') 361 362 key = self.ws.key() 363 resp = self.get( 364 headers={ 365 'Host': 'localhost', 366 'Upgrade': 'websocket', 367 'Connection': 'Upgrade', 368 'Sec-WebSocket-Key': key, 369 'Sec-WebSocket-Version': 13, 370 }, 371 read_timeout=1, 372 ) 373 374 self.assertEqual(resp['status'], 101, 'status') 375 self.assertEqual(resp['headers']['Upgrade'], 'websocket', 'upgrade') 376 self.assertEqual( 377 resp['headers']['Connection'], 'Upgrade', 'connection' 378 ) 379 self.assertEqual( 380 resp['headers']['Sec-WebSocket-Accept'], self.ws.accept(key), 'key' 381 ) 382 383 # autobahn-testsuite 384 # 385 # Some following tests fail because of Unit does not support UTF-8 386 # validation for websocket frames. It should be implemented 387 # by application, if necessary. 388 389 @unittest.skip('not yet') 390 def test_node_websockets_1_1_1__1_1_8(self): 391 self.load('websockets/mirror') 392 393 opcode = self.ws.OP_TEXT 394 395 _, sock, _ = self.ws.upgrade() 396 397 def check_length(length, chopsize=None): 398 payload = '*' * length 399 400 self.ws.frame_write(sock, opcode, payload, chopsize=chopsize) 401 402 frame = self.ws.frame_read(sock) 403 self.check_frame(frame, True, opcode, payload) 404 405 check_length(0) # 1_1_1 406 check_length(125) # 1_1_2 407 check_length(126) # 1_1_3 408 check_length(127) # 1_1_4 409 check_length(128) # 1_1_5 410 check_length(65535) # 1_1_6 411 check_length(65536) # 1_1_7 412 check_length(65536, chopsize = 997) # 1_1_8 413 414 self.close_connection(sock) 415 416 @unittest.skip('not yet') 417 def test_node_websockets_1_2_1__1_2_8(self): 418 self.load('websockets/mirror') 419 420 opcode = self.ws.OP_BINARY 421 422 _, sock, _ = self.ws.upgrade() 423 424 def check_length(length, chopsize=None): 425 payload = b'\xfe' * length 426 427 self.ws.frame_write(sock, opcode, payload, chopsize=chopsize) 428 frame = self.ws.frame_read(sock) 429 430 self.check_frame(frame, True, opcode, payload) 431 432 check_length(0) # 1_2_1 433 check_length(125) # 1_2_2 434 check_length(126) # 1_2_3 435 check_length(127) # 1_2_4 436 check_length(128) # 1_2_5 437 check_length(65535) # 1_2_6 438 check_length(65536) # 1_2_7 439 check_length(65536, chopsize = 997) # 1_2_8 440 441 self.close_connection(sock) 442 443 def test_node_websockets_2_1__2_6(self): 444 self.load('websockets/mirror') 445 446 op_ping = self.ws.OP_PING 447 op_pong = self.ws.OP_PONG 448 449 _, sock, _ = self.ws.upgrade() 450 451 def check_ping(payload, chopsize=None, decode=True): 452 self.ws.frame_write(sock, op_ping, payload, chopsize=chopsize) 453 frame = self.ws.frame_read(sock) 454 455 self.check_frame(frame, True, op_pong, payload, decode=decode) 456 457 check_ping('') # 2_1 458 check_ping('Hello, world!') # 2_2 459 check_ping(b'\x00\xff\xfe\xfd\xfc\xfb\x00\xff', decode=False) # 2_3 460 check_ping(b'\xfe' * 125, decode=False) # 2_4 461 check_ping(b'\xfe' * 125, chopsize=1, decode=False) # 2_6 462 463 self.close_connection(sock) 464 465 # 2_5 466 467 _, sock, _ = self.ws.upgrade() 468 469 self.ws.frame_write(sock, self.ws.OP_PING, b'\xfe' * 126) 470 self.check_close(sock, 1002) 471 472 def test_node_websockets_2_7__2_9(self): 473 self.load('websockets/mirror') 474 475 # 2_7 476 477 _, sock, _ = self.ws.upgrade() 478 479 self.ws.frame_write(sock, self.ws.OP_PONG, '') 480 self.assertEqual(self.recvall(sock, read_timeout=1), b'', '2_7') 481 482 # 2_8 483 484 self.ws.frame_write(sock, self.ws.OP_PONG, 'unsolicited pong payload') 485 self.assertEqual(self.recvall(sock, read_timeout=1), b'', '2_8') 486 487 # 2_9 488 489 payload = 'ping payload' 490 491 self.ws.frame_write(sock, self.ws.OP_PONG, 'unsolicited pong payload') 492 self.ws.frame_write(sock, self.ws.OP_PING, payload) 493 494 frame = self.ws.frame_read(sock) 495 self.check_frame(frame, True, self.ws.OP_PONG, payload) 496 497 self.close_connection(sock) 498 499 def test_node_websockets_2_10__2_11(self): 500 self.load('websockets/mirror') 501 502 # 2_10 503 504 _, sock, _ = self.ws.upgrade() 505 506 for i in range(0, 10): 507 self.ws.frame_write(sock, self.ws.OP_PING, 'payload-%d' % i) 508 509 for i in range(0, 10): 510 frame = self.ws.frame_read(sock) 511 self.check_frame(frame, True, self.ws.OP_PONG, 'payload-%d' % i) 512 513 # 2_11 514 515 for i in range(0, 10): 516 opcode = self.ws.OP_PING 517 self.ws.frame_write(sock, opcode, 'payload-%d' % i, chopsize=1) 518 519 for i in range(0, 10): 520 frame = self.ws.frame_read(sock) 521 self.check_frame(frame, True, self.ws.OP_PONG, 'payload-%d' % i) 522 523 self.close_connection(sock) 524 525 @unittest.skip('not yet') 526 def test_node_websockets_3_1__3_7(self): 527 self.load('websockets/mirror') 528 529 payload = 'Hello, world!' 530 531 # 3_1 532 533 _, sock, _ = self.ws.upgrade() 534 535 self.ws.frame_write(sock, self.ws.OP_TEXT, payload, rsv1=True) 536 self.check_close(sock, 1002) 537 538 # 3_2 539 540 _, sock, _ = self.ws.upgrade() 541 542 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 543 self.ws.frame_write(sock, self.ws.OP_TEXT, payload, rsv2=True) 544 self.ws.frame_write(sock, self.ws.OP_PING, '') 545 546 frame = self.ws.frame_read(sock) 547 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 548 549 self.check_close(sock, 1002, no_close=True) 550 551 self.assertEqual(self.recvall(sock, read_timeout=1), b'', 'empty 3_2') 552 sock.close() 553 554 # 3_3 555 556 _, sock, _ = self.ws.upgrade() 557 558 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 559 560 frame = self.ws.frame_read(sock) 561 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 562 563 self.ws.frame_write( 564 sock, self.ws.OP_TEXT, payload, rsv1=True, rsv2=True 565 ) 566 567 self.check_close(sock, 1002, no_close=True) 568 569 self.assertEqual(self.recvall(sock, read_timeout=1), b'', 'empty 3_3') 570 sock.close() 571 572 # 3_4 573 574 _, sock, _ = self.ws.upgrade() 575 576 self.ws.frame_write(sock, self.ws.OP_TEXT, payload, chopsize=1) 577 self.ws.frame_write( 578 sock, self.ws.OP_TEXT, payload, rsv3=True, chopsize=1 579 ) 580 self.ws.frame_write(sock, self.ws.OP_PING, '') 581 582 frame = self.ws.frame_read(sock) 583 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 584 585 self.check_close(sock, 1002, no_close=True) 586 587 self.assertEqual(self.recvall(sock, read_timeout=1), b'', 'empty 3_4') 588 sock.close() 589 590 # 3_5 591 592 _, sock, _ = self.ws.upgrade() 593 594 self.ws.frame_write( 595 sock, 596 self.ws.OP_BINARY, 597 b'\x00\xff\xfe\xfd\xfc\xfb\x00\xff', 598 rsv1=True, 599 rsv3=True, 600 ) 601 602 self.check_close(sock, 1002) 603 604 # 3_6 605 606 _, sock, _ = self.ws.upgrade() 607 608 self.ws.frame_write( 609 sock, self.ws.OP_PING, payload, rsv2=True, rsv3=True 610 ) 611 612 self.check_close(sock, 1002) 613 614 # 3_7 615 616 _, sock, _ = self.ws.upgrade() 617 618 self.ws.frame_write( 619 sock, self.ws.OP_CLOSE, payload, rsv1=True, rsv2=True, rsv3=True 620 ) 621 622 self.check_close(sock, 1002) 623 624 def test_node_websockets_4_1_1__4_2_5(self): 625 self.load('websockets/mirror') 626 627 payload = 'Hello, world!' 628 629 # 4_1_1 630 631 _, sock, _ = self.ws.upgrade() 632 633 self.ws.frame_write(sock, 0x03, '') 634 self.check_close(sock, 1002) 635 636 # 4_1_2 637 638 _, sock, _ = self.ws.upgrade() 639 640 self.ws.frame_write(sock, 0x04, 'reserved opcode payload') 641 self.check_close(sock, 1002) 642 643 # 4_1_3 644 645 _, sock, _ = self.ws.upgrade() 646 647 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 648 649 frame = self.ws.frame_read(sock) 650 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 651 652 self.ws.frame_write(sock, 0x05, '') 653 self.ws.frame_write(sock, self.ws.OP_PING, '') 654 655 self.check_close(sock, 1002) 656 657 # 4_1_4 658 659 _, sock, _ = self.ws.upgrade() 660 661 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 662 663 frame = self.ws.frame_read(sock) 664 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 665 666 self.ws.frame_write(sock, 0x06, payload) 667 self.ws.frame_write(sock, self.ws.OP_PING, '') 668 669 self.check_close(sock, 1002) 670 671 # 4_1_5 672 673 _, sock, _ = self.ws.upgrade() 674 675 self.ws.frame_write(sock, self.ws.OP_TEXT, payload, chopsize=1) 676 677 frame = self.ws.frame_read(sock) 678 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 679 680 self.ws.frame_write(sock, 0x07, payload, chopsize=1) 681 self.ws.frame_write(sock, self.ws.OP_PING, '') 682 683 self.check_close(sock, 1002) 684 685 # 4_2_1 686 687 _, sock, _ = self.ws.upgrade() 688 689 self.ws.frame_write(sock, 0x0B, '') 690 self.check_close(sock, 1002) 691 692 # 4_2_2 693 694 _, sock, _ = self.ws.upgrade() 695 696 self.ws.frame_write(sock, 0x0C, 'reserved opcode payload') 697 self.check_close(sock, 1002) 698 699 # 4_2_3 700 701 _, sock, _ = self.ws.upgrade() 702 703 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 704 705 frame = self.ws.frame_read(sock) 706 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 707 708 self.ws.frame_write(sock, 0x0D, '') 709 self.ws.frame_write(sock, self.ws.OP_PING, '') 710 711 self.check_close(sock, 1002) 712 713 # 4_2_4 714 715 _, sock, _ = self.ws.upgrade() 716 717 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 718 719 frame = self.ws.frame_read(sock) 720 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 721 722 self.ws.frame_write(sock, 0x0E, payload) 723 self.ws.frame_write(sock, self.ws.OP_PING, '') 724 725 self.check_close(sock, 1002) 726 727 # 4_2_5 728 729 _, sock, _ = self.ws.upgrade() 730 731 self.ws.frame_write(sock, self.ws.OP_TEXT, payload, chopsize=1) 732 733 frame = self.ws.frame_read(sock) 734 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 735 736 self.ws.frame_write(sock, 0x0F, payload, chopsize=1) 737 self.ws.frame_write(sock, self.ws.OP_PING, '') 738 739 self.check_close(sock, 1002) 740 741 def test_node_websockets_5_1__5_20(self): 742 self.load('websockets/mirror') 743 744 # 5_1 745 746 _, sock, _ = self.ws.upgrade() 747 748 self.ws.frame_write(sock, self.ws.OP_PING, 'fragment1', fin=False) 749 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=True) 750 self.check_close(sock, 1002) 751 752 # 5_2 753 754 _, sock, _ = self.ws.upgrade() 755 756 self.ws.frame_write(sock, self.ws.OP_PONG, 'fragment1', fin=False) 757 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=True) 758 self.check_close(sock, 1002) 759 760 # 5_3 761 762 _, sock, _ = self.ws.upgrade() 763 764 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 765 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=True) 766 767 frame = self.ws.frame_read(sock) 768 self.check_frame(frame, True, self.ws.OP_TEXT, 'fragment1fragment2') 769 770 # 5_4 771 772 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 773 self.assertEqual(self.recvall(sock, read_timeout=1), b'', '5_4') 774 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=True) 775 776 frame = self.ws.frame_read(sock) 777 self.check_frame(frame, True, self.ws.OP_TEXT, 'fragment1fragment2') 778 779 # 5_5 780 781 self.ws.frame_write( 782 sock, self.ws.OP_TEXT, 'fragment1', fin=False, chopsize=1 783 ) 784 self.ws.frame_write( 785 sock, self.ws.OP_CONT, 'fragment2', fin=True, chopsize=1 786 ) 787 788 frame = self.ws.frame_read(sock) 789 self.check_frame(frame, True, self.ws.OP_TEXT, 'fragment1fragment2') 790 791 # 5_6 792 793 ping_payload = 'ping payload' 794 795 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 796 self.ws.frame_write(sock, self.ws.OP_PING, ping_payload) 797 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=True) 798 799 frame = self.ws.frame_read(sock) 800 self.check_frame(frame, True, self.ws.OP_PONG, ping_payload) 801 802 frame = self.ws.frame_read(sock) 803 self.check_frame(frame, True, self.ws.OP_TEXT, 'fragment1fragment2') 804 805 # 5_7 806 807 ping_payload = 'ping payload' 808 809 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 810 self.assertEqual(self.recvall(sock, read_timeout=1), b'', '5_7') 811 812 self.ws.frame_write(sock, self.ws.OP_PING, ping_payload) 813 814 frame = self.ws.frame_read(sock) 815 self.check_frame(frame, True, self.ws.OP_PONG, ping_payload) 816 817 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=True) 818 819 frame = self.ws.frame_read(sock) 820 self.check_frame(frame, True, self.ws.OP_TEXT, 'fragment1fragment2') 821 822 # 5_8 823 824 ping_payload = 'ping payload' 825 826 self.ws.frame_write( 827 sock, self.ws.OP_TEXT, 'fragment1', fin=False, chopsize=1 828 ) 829 self.ws.frame_write(sock, self.ws.OP_PING, ping_payload, chopsize=1) 830 self.ws.frame_write( 831 sock, self.ws.OP_CONT, 'fragment2', fin=True, chopsize=1 832 ) 833 834 frame = self.ws.frame_read(sock) 835 self.check_frame(frame, True, self.ws.OP_PONG, ping_payload) 836 837 frame = self.ws.frame_read(sock) 838 self.check_frame(frame, True, self.ws.OP_TEXT, 'fragment1fragment2') 839 840 # 5_9 841 842 self.ws.frame_write( 843 sock, self.ws.OP_CONT, 'non-continuation payload', fin=True 844 ) 845 self.ws.frame_write(sock, self.ws.OP_TEXT, 'Hello, world!', fin=True) 846 self.check_close(sock, 1002) 847 848 # 5_10 849 850 _, sock, _ = self.ws.upgrade() 851 852 self.ws.frame_write( 853 sock, self.ws.OP_CONT, 'non-continuation payload', fin=True 854 ) 855 self.ws.frame_write(sock, self.ws.OP_TEXT, 'Hello, world!', fin=True) 856 self.check_close(sock, 1002) 857 858 # 5_11 859 860 _, sock, _ = self.ws.upgrade() 861 862 self.ws.frame_write( 863 sock, 864 self.ws.OP_CONT, 865 'non-continuation payload', 866 fin=True, 867 chopsize=1, 868 ) 869 self.ws.frame_write( 870 sock, self.ws.OP_TEXT, 'Hello, world!', fin=True, chopsize=1 871 ) 872 self.check_close(sock, 1002) 873 874 # 5_12 875 876 _, sock, _ = self.ws.upgrade() 877 878 self.ws.frame_write( 879 sock, self.ws.OP_CONT, 'non-continuation payload', fin=False 880 ) 881 self.ws.frame_write(sock, self.ws.OP_TEXT, 'Hello, world!', fin=True) 882 self.check_close(sock, 1002) 883 884 # 5_13 885 886 _, sock, _ = self.ws.upgrade() 887 888 self.ws.frame_write( 889 sock, self.ws.OP_CONT, 'non-continuation payload', fin=False 890 ) 891 self.ws.frame_write(sock, self.ws.OP_TEXT, 'Hello, world!', fin=True) 892 self.check_close(sock, 1002) 893 894 # 5_14 895 896 _, sock, _ = self.ws.upgrade() 897 898 self.ws.frame_write( 899 sock, 900 self.ws.OP_CONT, 901 'non-continuation payload', 902 fin=False, 903 chopsize=1, 904 ) 905 self.ws.frame_write( 906 sock, self.ws.OP_TEXT, 'Hello, world!', fin=True, chopsize=1 907 ) 908 self.check_close(sock, 1002) 909 910 # 5_15 911 912 _, sock, _ = self.ws.upgrade() 913 914 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 915 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=True) 916 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment3', fin=False) 917 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment4', fin=True) 918 self.check_close(sock, 1002) 919 920 # 5_16 921 922 _, sock, _ = self.ws.upgrade() 923 924 for i in range(0, 2): 925 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment1', fin=False) 926 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment2', fin=False) 927 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment3', fin=True) 928 self.check_close(sock, 1002) 929 930 # 5_17 931 932 _, sock, _ = self.ws.upgrade() 933 934 for i in range(0, 2): 935 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment1', fin=True) 936 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment2', fin=False) 937 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment3', fin=True) 938 self.check_close(sock, 1002) 939 940 # 5_18 941 942 _, sock, _ = self.ws.upgrade() 943 944 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 945 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment2') 946 self.check_close(sock, 1002) 947 948 # 5_19 949 950 _, sock, _ = self.ws.upgrade() 951 952 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 953 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=False) 954 self.ws.frame_write(sock, self.ws.OP_PING, 'pongme 1!') 955 956 time.sleep(1) 957 958 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment3', fin=False) 959 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment4', fin=False) 960 self.ws.frame_write(sock, self.ws.OP_PING, 'pongme 2!') 961 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment5') 962 963 frame = self.ws.frame_read(sock) 964 self.check_frame(frame, True, self.ws.OP_PONG, 'pongme 1!') 965 966 frame = self.ws.frame_read(sock) 967 self.check_frame(frame, True, self.ws.OP_PONG, 'pongme 2!') 968 969 self.check_frame( 970 self.ws.frame_read(sock), 971 True, 972 self.ws.OP_TEXT, 973 'fragment1fragment2fragment3fragment4fragment5', 974 ) 975 976 # 5_20 977 978 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 979 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2', fin=False) 980 self.ws.frame_write(sock, self.ws.OP_PING, 'pongme 1!') 981 982 frame = self.ws.frame_read(sock) 983 self.check_frame(frame, True, self.ws.OP_PONG, 'pongme 1!') 984 985 time.sleep(1) 986 987 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment3', fin=False) 988 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment4', fin=False) 989 self.ws.frame_write(sock, self.ws.OP_PING, 'pongme 2!') 990 991 frame = self.ws.frame_read(sock) 992 self.check_frame(frame, True, self.ws.OP_PONG, 'pongme 2!') 993 994 self.assertEqual(self.recvall(sock, read_timeout=1), b'', '5_20') 995 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment5') 996 997 self.check_frame( 998 self.ws.frame_read(sock), 999 True, 1000 self.ws.OP_TEXT, 1001 'fragment1fragment2fragment3fragment4fragment5', 1002 ) 1003 1004 self.close_connection(sock) 1005 1006 def test_node_websockets_6_1_1__6_4_4(self): 1007 self.load('websockets/mirror') 1008 1009 # 6_1_1 1010 1011 _, sock, _ = self.ws.upgrade() 1012 1013 self.ws.frame_write(sock, self.ws.OP_TEXT, '') 1014 frame = self.ws.frame_read(sock) 1015 self.check_frame(frame, True, self.ws.OP_TEXT, '') 1016 1017 # 6_1_2 1018 1019 self.ws.frame_write(sock, self.ws.OP_TEXT, '', fin=False) 1020 self.ws.frame_write(sock, self.ws.OP_CONT, '', fin=False) 1021 self.ws.frame_write(sock, self.ws.OP_CONT, '') 1022 1023 frame = self.ws.frame_read(sock) 1024 self.check_frame(frame, True, self.ws.OP_TEXT, '') 1025 1026 # 6_1_3 1027 1028 payload = 'middle frame payload' 1029 1030 self.ws.frame_write(sock, self.ws.OP_TEXT, '', fin=False) 1031 self.ws.frame_write(sock, self.ws.OP_CONT, payload, fin=False) 1032 self.ws.frame_write(sock, self.ws.OP_CONT, '') 1033 1034 frame = self.ws.frame_read(sock) 1035 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 1036 1037 # 6_2_1 1038 1039 payload = 'Hello-µ@ßöäüàá-UTF-8!!' 1040 1041 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 1042 1043 frame = self.ws.frame_read(sock) 1044 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 1045 1046 # 6_2_2 1047 1048 self.ws.frame_write(sock, self.ws.OP_TEXT, payload[:12], fin=False) 1049 self.ws.frame_write(sock, self.ws.OP_CONT, payload[12:]) 1050 1051 frame = self.ws.frame_read(sock) 1052 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 1053 1054 # 6_2_3 1055 1056 self.ws.message(sock, self.ws.OP_TEXT, payload, fragmention_size=1) 1057 1058 frame = self.ws.frame_read(sock) 1059 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 1060 1061 # 6_2_4 1062 1063 payload = '\xce\xba\xe1\xbd\xb9\xcf\x83\xce\xbc\xce\xb5' 1064 1065 self.ws.message(sock, self.ws.OP_TEXT, payload, fragmention_size=1) 1066 1067 frame = self.ws.frame_read(sock) 1068 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 1069 1070 self.close_connection(sock) 1071 1072# Unit does not support UTF-8 validation 1073# 1074# # 6_3_1 FAIL 1075# 1076# payload_1 = '\xce\xba\xe1\xbd\xb9\xcf\x83\xce\xbc\xce\xb5' 1077# payload_2 = '\xed\xa0\x80' 1078# payload_3 = '\x65\x64\x69\x74\x65\x64' 1079# 1080# payload = payload_1 + payload_2 + payload_3 1081# 1082# self.ws.message(sock, self.ws.OP_TEXT, payload) 1083# self.check_close(sock, 1007) 1084# 1085# # 6_3_2 FAIL 1086# 1087# _, sock, _ = self.ws.upgrade() 1088# 1089# self.ws.message(sock, self.ws.OP_TEXT, payload, fragmention_size=1) 1090# self.check_close(sock, 1007) 1091# 1092# # 6_4_1 ... 6_4_4 FAIL 1093 1094 def test_node_websockets_7_1_1__7_5_1(self): 1095 self.load('websockets/mirror') 1096 1097 # 7_1_1 1098 1099 _, sock, _ = self.ws.upgrade() 1100 1101 payload = "Hello World!" 1102 1103 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 1104 1105 frame = self.ws.frame_read(sock) 1106 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 1107 1108 self.close_connection(sock) 1109 1110 # 7_1_2 1111 1112 _, sock, _ = self.ws.upgrade() 1113 1114 self.ws.frame_write(sock, self.ws.OP_CLOSE, self.ws.serialize_close()) 1115 self.ws.frame_write(sock, self.ws.OP_CLOSE, self.ws.serialize_close()) 1116 1117 self.check_close(sock) 1118 1119 # 7_1_3 1120 1121 _, sock, _ = self.ws.upgrade() 1122 1123 self.ws.frame_write(sock, self.ws.OP_CLOSE, self.ws.serialize_close()) 1124 self.check_close(sock, no_close=True) 1125 1126 self.ws.frame_write(sock, self.ws.OP_PING, '') 1127 self.assertEqual(self.recvall(sock, read_timeout=1), b'', 'empty sock') 1128 1129 sock.close() 1130 1131 # 7_1_4 1132 1133 _, sock, _ = self.ws.upgrade() 1134 1135 self.ws.frame_write(sock, self.ws.OP_CLOSE, self.ws.serialize_close()) 1136 self.check_close(sock, no_close=True) 1137 1138 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 1139 self.assertEqual(self.recvall(sock, read_timeout=1), b'', 'empty sock') 1140 1141 sock.close() 1142 1143 # 7_1_5 1144 1145 _, sock, _ = self.ws.upgrade() 1146 1147 self.ws.frame_write(sock, self.ws.OP_TEXT, 'fragment1', fin=False) 1148 self.ws.frame_write(sock, self.ws.OP_CLOSE, self.ws.serialize_close()) 1149 self.check_close(sock, no_close=True) 1150 1151 self.ws.frame_write(sock, self.ws.OP_CONT, 'fragment2') 1152 self.assertEqual(self.recvall(sock, read_timeout=1), b'', 'empty sock') 1153 1154 sock.close() 1155 1156 # 7_1_6 1157 1158 _, sock, _ = self.ws.upgrade() 1159 1160 self.ws.frame_write(sock, self.ws.OP_TEXT, 'BAsd7&jh23' * 26 * 2 ** 10) 1161 self.ws.frame_write(sock, self.ws.OP_TEXT, payload) 1162 self.ws.frame_write(sock, self.ws.OP_CLOSE, self.ws.serialize_close()) 1163 1164 self.recvall(sock, read_timeout=1) 1165 1166 self.ws.frame_write(sock, self.ws.OP_PING, '') 1167 self.assertEqual(self.recvall(sock, read_timeout=1), b'', 'empty sock') 1168 1169 sock.close() 1170 1171 # 7_3_1 # FAIL 1172 1173 _, sock, _ = self.ws.upgrade() 1174 1175 self.ws.frame_write(sock, self.ws.OP_CLOSE, '') 1176 self.check_close(sock) 1177 1178 # 7_3_2 1179 1180 _, sock, _ = self.ws.upgrade() 1181 1182 self.ws.frame_write(sock, self.ws.OP_CLOSE, 'a') 1183 self.check_close(sock, 1002) 1184 1185 # 7_3_3 1186 1187 _, sock, _ = self.ws.upgrade() 1188 1189 self.ws.frame_write(sock, self.ws.OP_CLOSE, self.ws.serialize_close()) 1190 self.check_close(sock) 1191 1192 # 7_3_4 1193 1194 _, sock, _ = self.ws.upgrade() 1195 1196 payload = self.ws.serialize_close(reason='Hello World!') 1197 1198 self.ws.frame_write(sock, self.ws.OP_CLOSE, payload) 1199 self.check_close(sock) 1200 1201 # 7_3_5 1202 1203 _, sock, _ = self.ws.upgrade() 1204 1205 payload = self.ws.serialize_close(reason='*' * 123) 1206 1207 self.ws.frame_write(sock, self.ws.OP_CLOSE, payload) 1208 self.check_close(sock) 1209 1210 # 7_3_6 1211 1212 _, sock, _ = self.ws.upgrade() 1213 1214 payload = self.ws.serialize_close(reason='*' * 124) 1215 1216 self.ws.frame_write(sock, self.ws.OP_CLOSE, payload) 1217 self.check_close(sock, 1002) 1218 1219# # 7_5_1 FAIL Unit does not support UTF-8 validation 1220# 1221# _, sock, _ = self.ws.upgrade() 1222# 1223# payload = self.ws.serialize_close(reason = '\xce\xba\xe1\xbd\xb9\xcf' \ 1224# '\x83\xce\xbc\xce\xb5\xed\xa0\x80\x65\x64\x69\x74\x65\x64') 1225# 1226# self.ws.frame_write(sock, self.ws.OP_CLOSE, payload) 1227# self.check_close(sock, 1007) 1228 1229 def test_node_websockets_7_7_X__7_9_X(self): 1230 self.load('websockets/mirror') 1231 1232 valid_codes = [ 1233 1000, 1234 1001, 1235 1002, 1236 1003, 1237 1007, 1238 1008, 1239 1009, 1240 1010, 1241 1011, 1242 3000, 1243 3999, 1244 4000, 1245 4999, 1246 ] 1247 1248 invalid_codes = [0, 999, 1004, 1005, 1006, 1016, 1100, 2000, 2999] 1249 1250 for code in valid_codes: 1251 _, sock, _ = self.ws.upgrade() 1252 1253 payload = self.ws.serialize_close(code=code) 1254 1255 self.ws.frame_write(sock, self.ws.OP_CLOSE, payload) 1256 self.check_close(sock) 1257 1258 for code in invalid_codes: 1259 _, sock, _ = self.ws.upgrade() 1260 1261 payload = self.ws.serialize_close(code=code) 1262 1263 self.ws.frame_write(sock, self.ws.OP_CLOSE, payload) 1264 self.check_close(sock, 1002) 1265 1266 def test_node_websockets_7_13_1__7_13_2(self): 1267 self.load('websockets/mirror') 1268 1269 # 7_13_1 1270 1271 _, sock, _ = self.ws.upgrade() 1272 1273 payload = self.ws.serialize_close(code=5000) 1274 1275 self.ws.frame_write(sock, self.ws.OP_CLOSE, payload) 1276 self.check_close(sock, 1002) 1277 1278 # 7_13_2 1279 1280 _, sock, _ = self.ws.upgrade() 1281 1282 payload = struct.pack('!I', 65536) + ''.encode('utf-8') 1283 1284 self.ws.frame_write(sock, self.ws.OP_CLOSE, payload) 1285 self.check_close(sock, 1002) 1286 1287 def test_node_websockets_9_1_1__9_6_6(self): 1288 if not self.unsafe: 1289 self.skipTest("unsafe, long run") 1290 1291 self.load('websockets/mirror') 1292 1293 self.assertIn( 1294 'success', 1295 self.conf( 1296 { 1297 'http': { 1298 'websocket': { 1299 'max_frame_size': 33554432, 1300 'keepalive_interval': 0, 1301 } 1302 } 1303 }, 1304 'settings', 1305 ), 1306 'increase max_frame_size and keepalive_interval', 1307 ) 1308 1309 _, sock, _ = self.ws.upgrade() 1310 1311 op_text = self.ws.OP_TEXT 1312 op_binary = self.ws.OP_BINARY 1313 1314 def check_payload(opcode, length, chopsize=None): 1315 if opcode == self.ws.OP_TEXT: 1316 payload = '*' * length 1317 else: 1318 payload = b'*' * length 1319 1320 self.ws.frame_write(sock, opcode, payload, chopsize=chopsize) 1321 frame = self.ws.frame_read(sock, read_timeout=5) 1322 self.check_frame(frame, True, opcode, payload) 1323 1324 def check_message(opcode, f_size): 1325 if opcode == self.ws.OP_TEXT: 1326 payload = '*' * 4 * 2 ** 20 1327 else: 1328 payload = b'*' * 4 * 2 ** 20 1329 1330 self.ws.message(sock, opcode, payload, fragmention_size=f_size) 1331 frame = self.ws.frame_read(sock, read_timeout=5) 1332 self.check_frame(frame, True, opcode, payload) 1333 1334 check_payload(op_text, 64 * 2 ** 10) # 9_1_1 1335 check_payload(op_text, 256 * 2 ** 10) # 9_1_2 1336 check_payload(op_text, 2 ** 20) # 9_1_3 1337 check_payload(op_text, 4 * 2 ** 20) # 9_1_4 1338 check_payload(op_text, 8 * 2 ** 20) # 9_1_5 1339 check_payload(op_text, 16 * 2 ** 20) # 9_1_6 1340 1341 check_payload(op_binary, 64 * 2 ** 10) # 9_2_1 1342 check_payload(op_binary, 256 * 2 ** 10) # 9_2_2 1343 check_payload(op_binary, 2 ** 20) # 9_2_3 1344 check_payload(op_binary, 4 * 2 ** 20) # 9_2_4 1345 check_payload(op_binary, 8 * 2 ** 20) # 9_2_5 1346 check_payload(op_binary, 16 * 2 ** 20) # 9_2_6 1347 1348 if self.system != 'Darwin' and self.system != 'FreeBSD': 1349 check_message(op_text, 64) # 9_3_1 1350 check_message(op_text, 256) # 9_3_2 1351 check_message(op_text, 2 ** 10) # 9_3_3 1352 check_message(op_text, 4 * 2 ** 10) # 9_3_4 1353 check_message(op_text, 16 * 2 ** 10) # 9_3_5 1354 check_message(op_text, 64 * 2 ** 10) # 9_3_6 1355 check_message(op_text, 256 * 2 ** 10) # 9_3_7 1356 check_message(op_text, 2 ** 20) # 9_3_8 1357 check_message(op_text, 4 * 2 ** 20) # 9_3_9 1358 1359 check_message(op_binary, 64) # 9_4_1 1360 check_message(op_binary, 256) # 9_4_2 1361 check_message(op_binary, 2 ** 10) # 9_4_3 1362 check_message(op_binary, 4 * 2 ** 10) # 9_4_4 1363 check_message(op_binary, 16 * 2 ** 10) # 9_4_5 1364 check_message(op_binary, 64 * 2 ** 10) # 9_4_6 1365 check_message(op_binary, 256 * 2 ** 10) # 9_4_7 1366 check_message(op_binary, 2 ** 20) # 9_4_8 1367 check_message(op_binary, 4 * 2 ** 20) # 9_4_9 1368 1369 check_payload(op_text, 2 ** 20, chopsize=64) # 9_5_1 1370 check_payload(op_text, 2 ** 20, chopsize=128) # 9_5_2 1371 check_payload(op_text, 2 ** 20, chopsize=256) # 9_5_3 1372 check_payload(op_text, 2 ** 20, chopsize=512) # 9_5_4 1373 check_payload(op_text, 2 ** 20, chopsize=1024) # 9_5_5 1374 check_payload(op_text, 2 ** 20, chopsize=2048) # 9_5_6 1375 1376 check_payload(op_binary, 2 ** 20, chopsize=64) # 9_6_1 1377 check_payload(op_binary, 2 ** 20, chopsize=128) # 9_6_2 1378 check_payload(op_binary, 2 ** 20, chopsize=256) # 9_6_3 1379 check_payload(op_binary, 2 ** 20, chopsize=512) # 9_6_4 1380 check_payload(op_binary, 2 ** 20, chopsize=1024) # 9_6_5 1381 check_payload(op_binary, 2 ** 20, chopsize=2048) # 9_6_6 1382 1383 self.close_connection(sock) 1384 1385 def test_node_websockets_10_1_1(self): 1386 self.load('websockets/mirror') 1387 1388 _, sock, _ = self.ws.upgrade() 1389 1390 payload = '*' * 65536 1391 1392 self.ws.message(sock, self.ws.OP_TEXT, payload, fragmention_size=1300) 1393 1394 frame = self.ws.frame_read(sock) 1395 self.check_frame(frame, True, self.ws.OP_TEXT, payload) 1396 1397 self.close_connection(sock) 1398 1399 # settings 1400 1401 def test_node_websockets_max_frame_size(self): 1402 self.load('websockets/mirror') 1403 1404 self.assertIn( 1405 'success', 1406 self.conf( 1407 {'http': {'websocket': {'max_frame_size': 100}}}, 'settings' 1408 ), 1409 'configure max_frame_size', 1410 ) 1411 1412 _, sock, _ = self.ws.upgrade() 1413 1414 payload = '*' * 94 1415 opcode = self.ws.OP_TEXT 1416 1417 self.ws.frame_write(sock, opcode, payload) # frame length is 100 1418 1419 frame = self.ws.frame_read(sock) 1420 self.check_frame(frame, True, opcode, payload) 1421 1422 payload = '*' * 95 1423 1424 self.ws.frame_write(sock, opcode, payload) # frame length is 101 1425 self.check_close(sock, 1009) # 1009 - CLOSE_TOO_LARGE 1426 1427 def test_node_websockets_read_timeout(self): 1428 self.load('websockets/mirror') 1429 1430 self.assertIn( 1431 'success', 1432 self.conf( 1433 {'http': {'websocket': {'read_timeout': 5}}}, 'settings' 1434 ), 1435 'configure read_timeout', 1436 ) 1437 1438 _, sock, _ = self.ws.upgrade() 1439 1440 frame = self.ws.frame_to_send(self.ws.OP_TEXT, 'blah') 1441 sock.sendall(frame[:2]) 1442 1443 time.sleep(2) 1444 1445 self.check_close(sock, 1001) # 1001 - CLOSE_GOING_AWAY 1446 1447 def test_node_websockets_keepalive_interval(self): 1448 self.load('websockets/mirror') 1449 1450 self.assertIn( 1451 'success', 1452 self.conf( 1453 {'http': {'websocket': {'keepalive_interval': 5}}}, 'settings' 1454 ), 1455 'configure keepalive_interval', 1456 ) 1457 1458 _, sock, _ = self.ws.upgrade() 1459 1460 frame = self.ws.frame_to_send(self.ws.OP_TEXT, 'blah') 1461 sock.sendall(frame[:2]) 1462 1463 time.sleep(2) 1464 1465 frame = self.ws.frame_read(sock) 1466 self.check_frame(frame, True, self.ws.OP_PING, '') # PING frame 1467 1468 sock.close() 1469 1470 1471if __name__ == '__main__': 1472 TestNodeWebsockets.main() 1473