Summary:
I’m trying to run a WebSocket server using Ratchet and ReactPHP on my VPS. However, when executing server.php, I receive the following error:
PHP Fatal error: Uncaught RuntimeException: Failed to listen on "tcp://0.0.0.0:2053": Address already in use (EADDRINUSE) in /var/www/meetwithchat/vendor/react/socket/src/TcpServer.php:188
Even after killing the process that appears to be using port 2053, a new process is automatically restarted and binds to the same port. Consequently, my client-side code in script.js fails to establish a WebSocket connection.
I also get
WebSocket connection to 'wss://meetwithchat.com:2053/' failed:
Error on Chrome Console.
server.php:
<?php
use RatchetMessageComponentInterface;
use RatchetConnectionInterface;
require __DIR__ . '/vendor/autoload.php';
class ChatServer implements MessageComponentInterface {
// [Properties and constructor omitted for brevity]
public function onOpen(ConnectionInterface $conn) {
// [Code omitted for brevity]
}
public function onMessage(ConnectionInterface $from, $msg) {
// [Code omitted for brevity]
}
// Additional methods (matchUsers, endChatForBoth, onClose, onError)...
}
// Create the event loop
$loop = ReactEventLoopFactory::create();
// Set up the SSL context
$context = [
'ssl' => [
'local_cert' => '/etc/ssl/certs/cloudflare_origin.crt',
'local_pk' => '/etc/ssl/private/cloudflare_origin.key',
'allow_self_signed' => true,
'verify_peer' => false
]
];
// Create a TCP socket listening on all interfaces on port 2053
$socket = new ReactSocketServer('0.0.0.0:2053', $loop);
// Wrap it with SSL
$secureSocket = new ReactSocketSecureServer($socket, $loop, $context);
// Set up the WebSocket server
$server = new RatchetServerIoServer(
new RatchetHttpHttpServer(
new RatchetWebSocketWsServer(
new ChatServer()
)
),
$secureSocket,
$loop
);
error_log("Secure WebSocket server is running on port 2053...");
$server->run();
?>
script.js:
let ws = new WebSocket("wss://meetwithchat.com:2053/");
ws.onopen = function () {
// Send initial messages to set gender and preference
ws.send(JSON.stringify({ type: "setGender", gender: genderValue }));
ws.send(JSON.stringify({ type: "setPreference", preference: preferenceValue }));
};
ws.onmessage = function (event) {
const data = JSON.parse(event.data);
if (data.type === "match") {
// Handle a successful match
} else if (data.type === "message") {
// Append message to chat UI
} else if (data.type === "chatEnded") {
alert("Partner has left the chat. Chat ended!");
resetChat();
}
};
ws.onclose = function () {
resetChat();
};