Skip to content

Commit c996cde

Browse files
committed
update: 实施二进制传输与端到端加密支持
1 parent f5157cf commit c996cde

File tree

1 file changed

+32
-11
lines changed

1 file changed

+32
-11
lines changed

src/Server.php

+32-11
Original file line numberDiff line numberDiff line change
@@ -38,12 +38,16 @@ class Server
3838
private array $allowContentTypes = [
3939
'application/json',
4040
'application/x-compress',
41+
'application/x-e2e-compress+json',
42+
'application/x-e2e-json',
4143
];
4244

4345
private array $allowClient = [];
4446

45-
const PING_CONTENT = "\x05\x22\x09";
46-
const PONG_CONTENT = "\x05\x22\x0A";
47+
const PING_CONTENT = "\x05\x22\x09";
48+
const PONG_CONTENT = "\x05\x22\x0A";
49+
const FLAG_COMPRESS = 0x0001;
50+
const FLAG_ENCRYPTION = 0x0002;
4751

4852
public function __construct(
4953
protected LoggerInterface $logger,
@@ -278,9 +282,13 @@ private function onRequest(Request $request, Response $response): void
278282

279283
$rawBody = $request->getContent();
280284

281-
if ('application/x-compress' === $contentType) {
285+
$isCompress = 'application/x-compress' === $contentType || 'application/x-e2e-compress+json' === $contentType;
286+
$isEncryption = 'application/x-e2e-json' === $contentType || 'application/x-e2e-compress+json' === $contentType;
287+
288+
if ($isCompress && !$isEncryption) {
282289
$message = zlib_decode($rawBody);
283290
$messageSize = sprintf('%s(compress: %s)', format_byte(strlen($message)), format_byte(strlen($rawBody)));
291+
$isCompress = false;
284292
} else {
285293
$message = $rawBody;
286294
$messageSize = format_byte(strlen($message));
@@ -299,26 +307,39 @@ private function onRequest(Request $request, Response $response): void
299307
)
300308
);
301309

302-
$this->broadcast($clientId, $message);
310+
$this->broadcast($clientId, $message, $isCompress, $isEncryption);
303311
}
304312

305-
private function broadcast(string $clientId, string $message): void
313+
private function broadcast(string $clientId, string $message, bool $isCompress, bool $isEncryption): void
306314
{
307315
$fds = $this->broadcastMap[$clientId] ?? [];
308316
if (empty($fds)) {
309317
return;
310318
}
311319
$total = \count($fds);
312320
$i = 0;
321+
322+
$frameFlags = $isCompress
323+
? SWOOLE_WEBSOCKET_FLAG_FIN
324+
: SWOOLE_WEBSOCKET_FLAG_FIN | SWOOLE_WEBSOCKET_FLAG_COMPRESS;
325+
326+
$opcode = $isEncryption ? WEBSOCKET_OPCODE_BINARY : WEBSOCKET_OPCODE_TEXT;
327+
328+
if (WEBSOCKET_OPCODE_BINARY === $opcode) {
329+
$_f = 0;
330+
if ($isCompress) {
331+
$_f |= self::FLAG_COMPRESS;
332+
}
333+
if ($isEncryption) {
334+
$_f |= self::FLAG_ENCRYPTION;
335+
}
336+
$message = "\x05\x21" . pack('n', $_f) . $message;
337+
}
338+
313339
foreach ($fds as $fd) {
314340
$i++;
315341
$this->logger->debug("broadcast message to #{$fd}[{$i}/$total].");
316-
$this->server->push(
317-
$fd,
318-
$message,
319-
WEBSOCKET_OPCODE_TEXT,
320-
SWOOLE_WEBSOCKET_FLAG_FIN | SWOOLE_WEBSOCKET_FLAG_COMPRESS,
321-
);
342+
$this->server->push($fd, $message, $opcode, $frameFlags);
322343
}
323344
}
324345

0 commit comments

Comments
 (0)