WebSocket 프로토콜

현재 Workerman의 WebSocket 프로토콜 버전은 13입니다.

WebSocket 프로토콜은 HTML5의 새로운 프로토콜입니다. 이는 브라우저와 서버 간의 전이중 통신을 구현합니다.

WebSocket과 TCP 관계

WebSocket은 HTTP와 마찬가지로 응용 프로그램 계층 프로토콜이며, TCP 전송을 기반으로 합니다. WebSocket 자체와 소켓과는 큰 관계가 없으며, 동일시할 수 없습니다.

WebSocket 프로토콜 핸드셰이크

WebSocket 프로토콜에는 핸드셰이크 과정이 있으며, 핸드셰이크 시 브라우저와 서버는 HTTP 프로토콜로 통신합니다. Workerman에서는 핸드셰이크 과정에 이렇게 개입할 수 있습니다.

workerman <= 4.1일 때

<?php
require_once __DIR__ . '/vendor/autoload.php';

use Workerman\Connection\TcpConnection;
use Workerman\Worker;

$ws = new Worker('websocket://0.0.0.0:8181');
$ws->onConnect = function($connection)
{
    $connection->onWebSocketConnect = function($connection , $httpBuffer)
    {
        // 여기에서 연결 출처가 합법적인지 판단할 수 있으며, 불법적이면 연결을 종료합니다.
        // $_SERVER['HTTP_ORIGIN']은 어떤 사이트의 페이지에서 websocket 연결을 시도했는지를 나타냅니다.
        if($_SERVER['HTTP_ORIGIN'] != 'https://www.workerman.net')
        {
            $connection->close();
        }
        // onWebSocketConnect 내에서 $_GET $_SERVER는 사용 가능합니다.
        // var_dump($_GET, $_SERVER);
    };
};
Worker::runAll();

workerman >= 5.0일 때

<?php
require_once __DIR__ . '/vendor/autoload.php';

use Workerman\Connection\TcpConnection;
use Workerman\Protocols\Http\Request;
use Workerman\Worker;

$worker = new Worker('websocket://0.0.0.0:12345');
$worker->onWebSocketConnect = function (TcpConnection $connection, Request $request) {
    if ($request->header('origin') != 'https://www.workerman.net') {
        $connection->close();
    }
    var_dump($request->get());
    var_dump($request->header());
};
Worker::runAll();

WebSocket 프로토콜 이진 데이터 전송

WebSocket 프로토콜은 기본적으로 utf8 텍스트만 전송할 수 있으며, 이진 데이터를 전송하려면 아래 부분을 읽어보세요.

WebSocket 프로토콜에서는 프로토콜 헤더에 표시 비트를 사용하여 전송하는 데이터가 이진 데이터인지 utf8 텍스트 데이터인지를 표시합니다. 브라우저는 표시와 전송된 내용의 유형이 일치하는지 검증하며, 일치하지 않으면 오류를 발생시키고 연결을 끊습니다.

따라서 서버에서 데이터를 전송할 때는 전송 데이터 유형에 따라 이 표시 비트를 설정해야 하며, Workerman에서 일반 utf8 텍스트인 경우 이 값을 설정해야 합니다(기본적으로 이 값이므로 수동으로 설정할 필요는 없습니다).

use Workerman\Protocols\Websocket;
$connection->websocketType = Websocket::BINARY_TYPE_BLOB;

이진 데이터인 경우는 다음과 같이 설정해야 합니다.

use Workerman\Protocols\Websocket;
$connection->websocketType = Websocket::BINARY_TYPE_ARRAYBUFFER;

주의: 만약 $connection->websocketType를 설정하지 않은 경우, $connection->websocketType는 기본적으로 BINARY_TYPE_BLOB(즉, utf8 텍스트 유형)입니다. 일반적인 애플리케이션에서는 utf8 텍스트(예: JSON 데이터)를 전송하므로 $connection->websocketType를 수동으로 설정할 필요가 없습니다. 이진 데이터를 전송할 때만(예: 이미지 데이터, protobuffer 데이터 등) 이 속성을 BINARY_TYPE_ARRAYBUFFER로 설정해야 합니다.

Workerman을 WebSocket 클라이언트로 사용하기

AsyncTcpConnection 클래스ws 프로토콜을 조합하여 Workerman을 WebSocket 클라이언트로 사용하여 원격 WebSocket 서버에 연결하고 양방향 실시간 통신을 완료할 수 있습니다.