如何通过TCP将Laravel应用连接至Workerman服务器?
问题原因
你只用stream_socket_client建立了TCP连接,但没有向服务器发送完整的HTTP请求报文。浏览器访问时会自动发送标准的HTTP请求头(比如GET / HTTP/1.1、Host等字段),而你的代码仅建立连接就直接读取,服务器一直在等待请求数据,自然没有内容返回,导致stream_get_line返回false。
解决方案
建立连接后,先向服务器发送符合HTTP规范的请求,再读取响应内容。以下是修正后的Laravel控制器代码:
public function index() { try { $host = "127.0.0.1"; $port = 8080; // 建立TCP连接 $resource = stream_socket_client("tcp://$host:$port", $error_no, $error_str, 20, STREAM_CLIENT_CONNECT); if (!$resource) { throw new Exception("连接失败:$error_str ($error_no)"); } // 发送标准HTTP GET请求 $httpRequest = "GET / HTTP/1.1\r\n"; $httpRequest .= "Host: $host:$port\r\n"; $httpRequest .= "Connection: close\r\n\r\n"; // 空行表示请求头结束 fwrite($resource, $httpRequest); // 读取完整响应 $response = ''; while (!feof($resource)) { $response .= fread($resource, 8192); } // 关闭连接 fclose($resource); // 分离HTTP头和正文(可选,如果你只需要Hello world内容) list($headers, $body) = explode("\r\n\r\n", $response, 2); var_dump($body); // 这里会输出"Hello world" } catch(Exception $e){ return response($e->getMessage(), 500); } return View::make('index'); }
关键说明
- 必须发送完整的HTTP请求:HTTP协议要求请求包含请求行、请求头,最后以空行(
\r\n\r\n)结束,服务器才会处理并返回响应。 - 使用
fwrite发送请求数据,确保服务器能接收到完整的请求指令。 - 循环读取响应直到连接关闭(
feof),因为服务器返回的内容可能分块传输。
更简便的替代方案
如果不需要手动处理TCP连接,推荐使用PHP内置的file_get_contents或cURL,代码更简洁:
方案1:file_get_contents
public function index() { try { $response = file_get_contents("http://127.0.0.1:8080"); var_dump($response); // 直接输出Hello world } catch(Exception $e){ return response($e->getMessage(), 500); } return View::make('index'); }
方案2:cURL
public function index() { try { $ch = curl_init("http://127.0.0.1:8080"); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); $response = curl_exec($ch); curl_close($ch); var_dump($response); } catch(Exception $e){ return response($e->getMessage(), 500); } return View::make('index'); }
内容的提问来源于stack exchange,提问作者Jake
相关产品推荐
相关产品推荐

