(self)
| 157 | return b |
| 158 | |
| 159 | def read_next_message(self): |
| 160 | # noinspection PyBroadException |
| 161 | try: |
| 162 | decoded = '' |
| 163 | fin = 0 |
| 164 | while fin == 0: |
| 165 | head = None |
| 166 | try: |
| 167 | head = self.rfile.read(2) |
| 168 | except ValueError: |
| 169 | # socket was closed, just return without errors |
| 170 | return False |
| 171 | if head is None: |
| 172 | return False |
| 173 | if len(head) < 2: |
| 174 | return False |
| 175 | opcode = head[0] & 0b1111 |
| 176 | fin = head[0] >> 7 & 1 |
| 177 | is_masked = head[1] >> 7 & 1 |
| 178 | length = self.bytetonum(head[1]) & 127 |
| 179 | |
| 180 | if length == 126: |
| 181 | length = struct.unpack('>H', self.rfile.read(2))[0] |
| 182 | elif length == 127: |
| 183 | length = struct.unpack('>Q', self.rfile.read(8))[0] |
| 184 | |
| 185 | masks = [] |
| 186 | if is_masked: |
| 187 | masks = [self.bytetonum(byte) for byte in self.rfile.read(4)] |
| 188 | |
| 189 | frame_data = '' |
| 190 | for char in self.rfile.read(length): |
| 191 | if is_masked: |
| 192 | next_data = chr(self.bytetonum(char) ^ masks[len(frame_data) % 4]) |
| 193 | frame_data += next_data |
| 194 | else: |
| 195 | frame_data += chr(self.bytetonum(char)) |
| 196 | |
| 197 | decoded += frame_data |
| 198 | self._log.debug('read_message: %s...' % (decoded[:10])) |
| 199 | self.on_message(from_websocket(decoded)) |
| 200 | except socket.timeout: |
| 201 | return False |
| 202 | except Exception: |
| 203 | self._log.error('Error managing incoming websocket message', exc_info=True) |
| 204 | return False |
| 205 | return True |
| 206 | |
| 207 | def send_message(self, message): |
| 208 | if not self.handshake_done: |
no test coverage detected