php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #72977 cURL uses wrong domain when using user names with @ sign
Submitted: 2016-08-30 14:37 UTC Modified: 2016-08-30 22:09 UTC
From: rlwedelschaap at gmail dot com Assigned:
Status: Not a bug Package: cURL related
PHP Version: 7.0.10 OS: Ubuntu 16.04 LTS
Private report: No CVE-ID: None
 [2016-08-30 14:37 UTC] rlwedelschaap at gmail dot com
Description:
------------
When using a user name and password for basic authentication in the URL directly, cURL will try to resolve the domain from the user name when the user name contains an @ sign instead of the actual domain.

This results in
a) requesting the wrong URL when the domain in the user name exists;
b) a "Could not resolve host" error when the domain in the user name does not exist.



Test script:
---------------
<?php
    $curl = curl_init();

    curl_setopt_array( $curl, [
        CURLOPT_FOLLOWLOCATION => true,
        CURLOPT_FORBID_REUSE   => true,
        CURLOPT_FRESH_CONNECT  => true,
        CURLOPT_HEADER         => false,
        CURLOPT_HTTPHEADER     => [
            'Accept: text/html,application/json,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
            'Accept-Charset: UTF-8',
            'Connection: close',
            'Content-Type: charset=UTF-8',
        ],
        CURLOPT_MAXREDIRS      => 3,
        CURLOPT_RETURNTRANSFER => true,
        CURLOPT_SSL_VERIFYPEER => false,
        CURLOPT_TIMEOUT        => 30,
        CURLOPT_URL            => 'http://user@domain.com:password@www.example.com/page.html',
    ] );

    $response = curl_exec( $curl );

    if ( $response !== false ) {
        echo 'Completed cURL exec';
        print_r( curl_getinfo( $curl ) );
    } else {
        echo 'Error: ' . curl_error( $curl );
        print_r( curl_getinfo( $curl ) );
    }

Expected result:
----------------
Completed cURL exec

Array
(
    [url] => http://user@domain.com:password@www.example.com/page.html
    [content_type] => text/html; charset=UTF-8
    [http_code] => 200
    ...
)


/* $response should contain the HTML page of http://www.example.com/page.html */

Actual result:
--------------
Completed cURL exec

Array
(
    [url] => http://www.domain.com/page
    [content_type] => text/html; charset=UTF-8
    [http_code] => 200
    ...
)

/* In this scenario, $response contains the HTML page of http://www.domain.com/page */

===== Or, when using a non-existing domain in the user name =====

Error: Could not resolve host: a-non-existing-domain.com

Array
(
    [url] => http://user@a-non-existing-domain.com:password@www.example.com/page.html
    [content_type] => 
    [http_code] => 0
    ...
)

Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2016-08-30 22:09 UTC] requinix@php.net
-Status: Open +Status: Not a bug
 [2016-08-30 22:09 UTC] requinix@php.net
As per RFC 3986 the only characters permitted for a username or password are letters, digits, %s used for percent encoding, and -._~!$&'()*+,;= so any @s must be encoded.

Use rawurlencode() on the username and password (separately) before putting them into the URL.

$user = rawurlencode('user@domain.com');
$password = rawurlencode('password');
$url = "http://{$user}:{$password}@www.example.com/page.html";
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Wed Dec 11 19:01:27 2024 UTC