PHP의 Socket_set_blocking 함수는 소켓 자원의 차단 모드를 설정하는 데 사용됩니다.
차단 모드 : 소켓 관련 기능을 호출 할 때 작업이 완료 될 때까지 기다리면이 기간 동안 프로그램이 일시 중지됩니다.
비 블로킹 모드 : 소켓 관련 기능을 호출 할 때 즉시 반환하고 작동이 완료되기를 기다리지 않습니다.
기본적으로 소켓이 차단됩니다. 차단 모드는 간단한 동기화 시나리오에 적합하지만 고성능 서버에는보다 자세한 제어 흐름 메커니즘이 필요합니다.
bool socket_set_blocking ( resource $socket , bool $mode )
$ 소켓 : 소켓 리소스.
$ 모드 : True는 차단을 의미하며, 잘못된 것은 차단을 의미합니다.
Control Flow는 메시지의 전송 및 수신 리듬을 관리하여 메시지가 너무 빨리 전송되는 것을 방지하여 네트워크 혼잡, 과도한 리소스 사용 또는 메시지 손실이 발생합니다. 제어 흐름이있는 설계는 다음을 달성 할 수 있습니다.
큐 메시지 버퍼링, 단계별로 전송.
차단 모드와 비 블로킹 모드 사이를 동적으로 전환합니다.
시간 초과 처리 및 오류 재시도 메커니즘.
서버와 클라이언트는 모두 차단 모드를 사용하여 전송 및 수신의 안정성을 보장합니다.
메시지 전송 대기열을 대기하고 보낸 버퍼에 데이터가있을 때만 차단 및 대기를 방지합니다.
수신기는 장기간 교수형을 피하기 위해 합리적인 시간 초과를 설정합니다.
Socket_Select를 사용하여 멀티플렉싱을 달성하고 읽기 및 쓰기 이벤트를 모니터링하며 효율성을 향상시킵니다.
다음은 단순화 된 TCP 기반 PHP 소켓 서버 예제로, 소켓 _set_blocking을 사용하여 차단 모드를 제어하여 메시징의 흐름 제어를 실현하는 방법을 보여줍니다.
<?php
$host = "0.0.0.0";
$port = 12345;
// 만들다socket
$sock = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
socket_bind($sock, $host, $port);
socket_listen($sock);
echo "Server started at $host:$port\n";
// 모니터링을 설정하십시오socket차단 모드에서,연결을 수락 할 때 클라이언트를 기다리고 있습니다
socket_set_blocking($sock, true);
$clients = [];
while (true) {
// 사용 socket_select 활성 연결을 듣습니다
$read = $clients;
$read[] = $sock; // 모니터에 가입하십시오socket
$write = [];
$except = null;
// 활동 대기 차단socket
if (socket_select($read, $write, $except, 5) < 1) {
continue; // 시간 초과 활동 없음
}
// 새로운 연결을 처리하십시오
if (in_array($sock, $read)) {
$newClient = socket_accept($sock);
if ($newClient !== false) {
socket_set_blocking($newClient, true); // 클라이언트 설정socket차단을 위해,완전한 메시지를 보장합니다
$clients[] = $newClient;
echo "New client connected\n";
}
unset($read[array_search($sock, $read)]);
}
// 기존 클라이언트 메시지를 처리합니다
foreach ($read as $client) {
$data = socket_read($client, 2048, PHP_NORMAL_READ);
if ($data === false || $data === '') {
// 클라이언트 단절
echo "Client disconnected\n";
socket_close($client);
unset($clients[array_search($client, $clients)]);
continue;
}
$data = trim($data);
echo "Received: $data\n";
// 간단한 에코,흐름 제어와 함께:보내기 전에 확인하십시오socket차단 모드,쓰기 실패를 방지하십시오
socket_set_blocking($client, true);
$sendResult = socket_write($client, "Echo: $data\n");
if ($sendResult === false) {
echo "Failed to send message to client\n";
}
}
}
차단 모드의 전환 <br> 청취 소켓과 클라이언트 소켓이 모두 차단으로 설정되어 데이터를 읽고 쓰면 데이터의 무결성을 보장 할 수 있으며 비 블로킹 모드에서 짧은 읽기 및 짧은 쓰기로 인해 불완전한 메시지를 피하십시오.
socket_select 수다 더 많은 청취
Socket_select 소켓을 읽을 수있을 때까지 대기하고 대기하여 CPU 활용을 개선하고 죽은 루프에서 자원 낭비를 피합니다.
메시지 대기열 제어 (확장 가능)
예제에서 직접 읽고 작성되지만 클라이언트 네트워크 혼잡을 피하기 위해 전송 된 각 메시지의 크기와 주파수를 제어 할 필요성에 따라 메시지 대기열을 추가 할 수 있습니다.
비 블로킹 모드를 사용하여 이벤트 중심 라이브러리 (예 : Libevent)와 협력하여 동시성 성능이 높아집니다.
메시지 전송의 무결성을 보장하기 위해 메시지 일련 번호 및 확인 메커니즘을 소개합니다.
하트 비트 패킷 감지 연결 상태를 구현하십시오.
Socket_set_option을 사용하여 대기 시간을 줄이기 위해 TCP_NODELAY 설정과 같은 TCP 매개 변수를 최적화하십시오.
PHP의 socket_set_blocking 함수를 합리적으로 사용하고 socket_select 이벤트 청취 메커니즘을 결합하면 효율적인 메시징 및 수신 시스템이 제어 흐름을 구축 할 수 있습니다. 제어 흐름은 메시지 전송의 안정성을 보장 할뿐만 아니라 시스템의 응답 속도 및 리소스 활용도를 향상시킵니다. 이 기사의 예와 아이디어가 자신의 메시지 시스템을 구축하는 데 도움이되기를 바랍니다.