php的socket通訊

什麼是TCP/IP、UDP?
TCP/IP(Transmission Control Protocol/Internet Protocol)即傳輸控制協議/網間協議,是一個工業標準的協議集,它是爲廣域網(WANs)設計的。TCP/IP協議族包括運輸層、網絡層、鏈路層。
UDP(User Data Protocol,用戶數據報協議)是與TCP相對應的協議。它是屬於TCP/IP協議族中的一種。
這裏有一張圖,代表了這些協議的關係。php

Socket在哪裏呢?設計模式

原來Socket在這裏。以下圖:數組

Socket是什麼呢?
Socket是應用層與TCP/IP協議族通訊的中間軟件抽象層,它是一組接口。在設計模式中,Socket其實就是一個門面模式,它把複雜的TCP/IP協議族隱藏在Socket接口後面,對用戶來講,一組簡單的接口就是所有,讓Socket去組織數據,以符合指定的協議。緩存

先從服務器端提及。服務器端先初始化Socket,而後與端口綁定(bind),對端口進行監聽(listen),調用accept阻塞,等待客戶端鏈接。在這時若是有個客戶端初始化一個Socket,而後鏈接服務器(connect),若是鏈接成功,這時客戶端與服務器端的鏈接就創建了。客戶端發送數據請求,服務器端接收請求並處理請求,而後把迴應數據發送給客戶端,客戶端讀取數據,最後關閉鏈接,一次交互結束。
socket相關函數:
----------------------------------------------------------------------------------------------
socket_accept() 接受一個Socket鏈接
socket_bind() 把socket綁定在一個IP地址和端口上
socket_clear_error() 清除socket的錯誤或者最後的錯誤代碼
socket_close() 關閉一個socket資源
socket_connect() 開始一個socket鏈接
socket_create_listen() 在指定端口打開一個socket監聽
socket_create_pair() 產生一對沒有區別的socket到一個數組裏
socket_create() 產生一個socket,至關於產生一個socket的數據結構
socket_get_option() 獲取socket選項
socket_getpeername() 獲取遠程相似主機的ip地址
socket_getsockname() 獲取本地socket的ip地址
socket_iovec_add() 添加一個新的向量到一個分散/聚合的數組
socket_iovec_alloc() 這個函數建立一個可以發送接收讀寫的iovec數據結構
socket_iovec_delete() 刪除一個已經分配的iovec
socket_iovec_fetch() 返回指定的iovec資源的數據
socket_iovec_free() 釋放一個iovec資源
socket_iovec_set() 設置iovec的數據新值
socket_last_error() 獲取當前socket的最後錯誤代碼
socket_listen() 監聽由指定socket的全部鏈接
socket_read() 讀取指定長度的數據
socket_readv() 讀取從分散/聚合數組過來的數據
socket_recv() 從socket裏結束數據到緩存
socket_recvfrom() 接受數據從指定的socket,若是沒有指定則默認當前socket
socket_recvmsg() 從iovec裏接受消息
socket_select() 多路選擇
socket_send() 這個函數發送數據到已鏈接的socket
socket_sendmsg() 發送消息到socket
socket_sendto() 發送消息到指定地址的socket
socket_set_block() 在socket裏設置爲塊模式
socket_set_nonblock() socket裏設置爲非塊模式
socket_set_option() 設置socket選項
socket_shutdown() 這個函數容許你關閉讀、寫、或者指定的socket
socket_strerror() 返回指定錯誤號的詳細錯誤
socket_write() 寫數據到socket緩存
socket_writev() 寫數據到分散/聚合數組服務器

案例:代碼詳解
server.php
<?php
error_reporting(E_ALL);
set_time_limit(0);
ob_implicit_flush();
// IP
$host = 'localhost';
// 端口
$port = 11111;
// 建立一個Socket(socket_create()函數建立一個Socket,這個函數返回一個Socket句柄,此句柄將用在之後全部網絡

的函數中)
$socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP) or die("Could not create server socket\n");
// 綁定Socket到指定地址和端口
$result = socket_bind($socket, $host, $port) or die("Could not bind to socket\n");
// 監聽外部的鏈接
$result = socket_listen($socket, 3) or die("Could not set up socket listener\n");
// 等待並接收來自客戶端的鏈接請求(accept incoming connections from client)
// (socket_accept()函數接收來自客戶端的鏈接請求,並調用另外一個子Socket來處理客戶端–服務器間的信息)
$spawn = socket_accept($socket) or die("Could not accept incoming connection from client\n");
echo "Reading Information From Client:\n";
// 得到客戶端的輸入
$fromCli = socket_read($spawn, 1024) or die("Could not read client input\n");
// 處理客戶端輸入並返回結果
$fromCli = trim($fromCli);
echo $fromCli;
echo "Reading Information From Client End......\n";
echo "Send Command To Client......";
$toCli = "Hello Client:\nWhat can i do for u?\n";
socket_write($spawn, $toCli, strlen ($toCli)) or die("Could not write output\n");
echo "Send End......\n";
// 關閉sockets
echo "Close socket connection......\n";
socket_close($spawn);
echo "OK, socket connection closed......\n";
echo "Close server socket......\n";
socket_close($socket);
echo "OK, server socket closed......\n";數據結構

client.php
<?php
error_reporting(E_ALL);
set_time_limit(0);
// IP
$address = 'localhost';
// 端口
$serPort = 11111;
$socket = socket_create(AF_INET,SOCK_STREAM,SOL_TCP) or die("Could not create client socket\n");
$conn = socket_connect($socket,$address,$serPort) or die("Could not connect to server\n");
// 發送數據
echo "Send Command To Server......";
$toSer = "HEAD / HTTP/1.1\nConnection:Close\nHello Server!!!\n";
socket_write($socket,$toSer,strlen($toSer));
echo "Send End......\n";
echo "Reading Information From Server:\n";
while($fromSer = socket_read($socket,2048)){
    echo $fromSer;
}
echo "Reading Information From Server End......\n";
echo "Close client socket......\n";
socket_close($socket);
echo "OK, client socket closed......\n";socket

相關文章
相關標籤/搜索