reactphp / http

Event-driven, streaming HTTP client and server implementation for ReactPHP.
https://reactphp.org/http/
MIT License
740 stars 142 forks source link

Cannot create socket server #490

Closed designermonkey closed 1 year ago

designermonkey commented 1 year ago

Using the code below (very similar to the examples), I cannot create a socket connection without getting an error. I've tried multiple IP and port combinations of 127.0.0.1 and 0.0.0.0 and many ports that I know are free, both in a Docker container specifically built for PHP CLI, and on my local PHP 8.2 install.

My code:

<?php declare(strict_types=1);

require __DIR__ . '/vendor/autoload.php';

use Psr\Http\Message\ServerRequestInterface;
use React\Http\HttpServer;
use React\Http\Message\Response;
use React\Socket\SocketServer;

$http = new HttpServer(function (ServerRequestInterface $request) {
    $body = "The method of the request is: " . $request->getMethod() . "\n";
    $body .= "The requested path is: " . $request->getUri()->getPath() . "\n";

    return Response::plaintext(
        $body
    );
 });

$socket = new SocketServer('0.0.0.0:1337');

$http->listen($socket);

echo 'Listening on ' . str_replace('tcp:', 'http:', $socket->getAddress()) . PHP_EOL;

My error:

$ php -f main.php 
Listening on http://0.0.0.0:1337
PHP Fatal error:  Uncaught RuntimeException: Failed to listen on "tcp://0.0.0.0:1337": Address already in use (EADDRINUSE) in /Users/porterj/Projects/datum.micron-research.net/datum-api/vendor/react/socket/src/TcpServer.php:184
Stack trace:
#0 /Users/porterj/Projects/datum.micron-research.net/datum-api/vendor/react/socket/src/SocketServer.php(61): React\Socket\TcpServer->__construct('tcp://0.0.0.0:1...', NULL, Array)
#1 /Users/porterj/Projects/datum.micron-research.net/datum-api/main.php(19): React\Socket\SocketServer->__construct('0.0.0.0:1337')
#2 {main}
  thrown in /Users/porterj/Projects/datum.micron-research.net/datum-api/vendor/react/socket/src/TcpServer.php on line 184

Fatal error: Uncaught RuntimeException: Failed to listen on "tcp://0.0.0.0:1337": Address already in use (EADDRINUSE) in /Users/porterj/Projects/datum.micron-research.net/datum-api/vendor/react/socket/src/TcpServer.php:184
Stack trace:
#0 /Users/porterj/Projects/datum.micron-research.net/datum-api/vendor/react/socket/src/SocketServer.php(61): React\Socket\TcpServer->__construct('tcp://0.0.0.0:1...', NULL, Array)
#1 /Users/porterj/Projects/datum.micron-research.net/datum-api/main.php(19): React\Socket\SocketServer->__construct('0.0.0.0:1337')
#2 {main}
  thrown in /Users/porterj/Projects/datum.micron-research.net/datum-api/vendor/react/socket/src/TcpServer.php on line 184

I looked into the TcpServer and found where it was trying to make a socket connection, so I tried it myself:

<?php

$uri = '127.0.0.1:1337';

$master = @\stream_socket_server(
    $uri,
    $errno,
    $errstr,
    \STREAM_SERVER_BIND | \STREAM_SERVER_LISTEN,
    \stream_context_create(array('socket' => array('backlog' => 511)))
);

var_dump($errno, $errstr, $master);

This above seems to work fine, so I don't understand why it doesn't ever work in the ReactPHP code.

When I tried to use 0 as a port, my code worked fine, but I did notice that it echoed twice. Does this mean that it is being run twice? That would indeed cause an error, but I cannot for the life of me figure out why it would run twice.

Any help would be appreciated.

WyriHaximus commented 1 year ago

When I tried to use 0 as a port, my code worked fine, but I did notice that it echoed twice. Does this mean that it is being run twice? That would indeed cause an error, but I cannot for the life of me figure out why it would run twice.

Do you mean you are seeing this line twice? If yes, then yes it's being run twice.

Listening on http://0.0.0.0:1337

Just tried your script and had no issues starting it. What is the list of packages installed?

SimonFrings commented 1 year ago

@designermonkey I also tried out the example and it works fine on my system. I don't think this is a bug in https://github.com/reactphp, so I'll close this for now.

I'd suggest to open up a new discussion in our Q&A category and we can discuss your problem further in there. Can you also give us a bit more information about the steps you took to get there, this can help us to reproduce the exact same pattern and find an answer.

designermonkey commented 1 year ago

I hate when this happens: Interestingly, if I run it as a shell executable with #!/usr/bin/env php at the top, it works fine... It now also works fine without the hashbang.

Why does code do this to us? Thanks for your time though.