使用textalk/websocket-php连接socket.io服务器失败求助
使用textalk/websocket-php连接Socket.IO服务器的持久连接问题
Node端Socket.IO配置
server = httpServ.createServer().listen(process.env.PORT); //3000 let socketCorsConfig = { origin: "*:*" } const io = require('socket.io')(server, { path: '/ws', serveClient: false, pingInterval: 10000, pingTimeout: 5000, cookie: false, cors: socketCorsConfig }); io.use(async (socket, next) => { console.log('middleware'); ... }); io.on('connection', async socket => { console.log('connection, socket: ' + socket.id); ... });
PHP(Symfony)端客户端代码
use WebSocket\Client as WSClient; ... $wsClient = new WSClient('ws://php-websocket:3000/ws/?EIO=4&transport=websocket'); while(true){ $message = $wsClient->receive(); dump('Data', $message); } $wsClient->close();
控制台输出
Data 0{"sid":"H3I27EP0LH-JOJWvAAAI","upgrades":[],"pingInterval":10000,"pingTimeout":5000,"maxPayload":1000000} Data Data 0{"sid":"nIij79dNorR_kYxOAAAJ","upgrades":[],"pingInterval":10000,"pingTimeout":5000,"maxPayload":1000000} In Connection.php line 464: Client read timeout
排查建议
- 处理Socket.IO心跳机制:Socket.IO服务器会定期发送ping包,textalk/websocket-php作为原生WebSocket客户端不会自动处理该逻辑,需手动解析消息,当收到前缀为
2的ping包时,回复3作为pong响应,否则服务器会判定连接超时断开。 - 调整客户端超时参数:初始化WSClient时延长超时时间,避免因心跳等待触发超时,示例配置:
$wsClient = new WSClient('ws://php-websocket:3000/ws/?EIO=4&transport=websocket', [ 'timeout' => 60, 'connection_timeout' => 10 ]); - 解析Socket.IO消息格式:Socket.IO消息带有前缀标识(如
0代表连接确认),需剥离前缀后处理内容,空消息可能是解析异常导致,要增加消息校验逻辑。 - 排查重复连接问题:控制台出现两次不同sid,说明PHP客户端可能重复发起连接,检查代码是否存在多次实例化WSClient的逻辑。
- 更换Socket.IO专用PHP客户端:textalk/websocket-php仅支持原生WebSocket协议,对Socket.IO的上层协议兼容有限,建议使用专门的Socket.IO PHP客户端库(如
workerman/socket.io),这类库会自动处理握手、心跳和消息编码逻辑。
内容的提问来源于stack exchange,提问作者ArturoO
相关产品推荐
相关产品推荐

