How to create asynchronous HTTP request in PHP

While creating HTTP request to other websites,  sometimes we don't need to get response from the server. In this case we have to just send the HTTP request and should drop the connection, so we don't wait until request complete and complete the next process.

This can be done from using sockets if we don't need to check about the response from the request. This is because socket connection can be terminated straight after sending the request without waiting. This is like fire and forget the request.

To use the socket connection, there is fsockopen() function in PHP. I have used this function to send the HTTP request.

Here is my full code to send HTTP request.

/**
 * Send a HTTP request, but do not wait for the response
 *
 * @param string $method The HTTP method
 * @param string $url The url (including query string)
 * @param array $params Added to the URL or request body depending on method
 */
public function sendRequest(string $method, string $url, array $params = []): void
{
    // url check
    $parts = parse_url($url);
    if ($parts === false)
        throw new Exception('Unable to parse URL');
    $host = $parts['host'] ?? null;
    $port = $parts['port'] ?? 80;
    $path = $parts['path'] ?? '/';
    $query = $parts['query'] ?? '';
    parse_str($query, $queryParts);

    if ($host === null)
        throw new Exception('Unknown host');
    $connection = fsockopen($host, $port, $errno, $errstr, 30);
    if ($connection === false)
        throw new Exception('Unable to connect to ' . $host);
    $method = strtoupper($method);

    if (!in_array($method, ['POST', 'PUT', 'PATCH'], true)) {
        $queryParts = $params + $queryParts;
        $params = [];
    }

    // Build request
    $request  = $method . ' ' . $path;
    if ($queryParts) {
        $request .= '?' . http_build_query($queryParts);
    }
    $request .= ' HTTP/1.1' . "\r\n";
    $request .= 'Host: ' . $host . "\r\n";

    $body = http_build_query($params);
    if ($body) {
        $request .= 'Content-Type: application/x-www-form-urlencoded' . "\r\n";
        $request .= 'Content-Length: ' . strlen($body) . "\r\n";
    }
    $request .= 'Connection: Close' . "\r\n\r\n";
    $request .= $body;

    // Send request to server
    fwrite($connection, $request);
    fclose($connection);
}

With this function, you can simply send asynchronous HTTP request. If you have any suggestions please make comment bellow, would be much appreciated.

Tags: