ChatGPT解决这个技术问题 Extra ChatGPT

PHP - Debugging Curl

I'd like to see what the post fields in the request are before I send it. (For debugging purposes).

The PHP library (class) I am using is already made (not by me), so I am trying to understand it.

As far as I can tell, it uses curl_setopt() to set different options like headers and such and then it uses curl_exec() to send the request.

Ideas on how to see what post fields are being sent?


h
hakre

You can enable the CURLOPT_VERBOSE option Curl, PHP and log that information to a (temporary) CURLOPT_STDERR:

// CURLOPT_VERBOSE: TRUE to output verbose information.
// Writes output to STDERR, 
// -or- the file specified using CURLOPT_STDERR.
curl_setopt($curlHandle, CURLOPT_VERBOSE, true);

$streamVerboseHandle = fopen('php://temp', 'w+');
curl_setopt($curlHandle, CURLOPT_STDERR, $streamVerboseHandle);

You can then read it after curl has done the request:

$result = curl_exec($curlHandle);
if ($result === FALSE) {
    printf("cUrl error (#%d): %s<br>\n",
           curl_errno($curlHandle),
           htmlspecialchars(curl_error($curlHandle)))
           ;
}

rewind($streamVerboseHandle);
$verboseLog = stream_get_contents($streamVerboseHandle);

echo "cUrl verbose information:\n", 
     "<pre>", htmlspecialchars($verboseLog), "</pre>\n";

(I originally answered similar but more extended in a related question.)

More information like metrics about the last request is available via curl_getinfo. This information can be useful for debugging curl requests, too. A usage example, I would normally wrap that into a function:

$version = curl_version();
extract(curl_getinfo($curlHandle));
$metrics = <<<EOD
URL....: $url
Code...: $http_code ($redirect_count redirect(s) in $redirect_time secs)
Content: $content_type Size: $download_content_length (Own: $size_download) Filetime: $filetime
Time...: $total_time Start @ $starttransfer_time (DNS: $namelookup_time Connect: $connect_time Request: $pretransfer_time)
Speed..: Down: $speed_download (avg.) Up: $speed_upload (avg.)
Curl...: v{$version['version']}
EOD;

fopen option should be 'w+'
@iisisrael: You are right. Corrected. Thanks for the hint.
Before you jump into debugging, however: Try checking the apache log in case an error was tossed (like curl php not being installed, so the function failed!)
J
JamesG

You can enable the CURLOPT_VERBOSE option:

curl_setopt($curlhandle, CURLOPT_VERBOSE, true);

When CURLOPT_VERBOSE is set, output is written to STDERR or the file specified using CURLOPT_STDERR. The output is very informative.

You can also use tcpdump or wireshark to watch the network traffic.


It is worth noting that this will not work if you have set CURLINFO_HEADER_OUT to TRUE. So far as I can tell...
Than work $info = curl_getinfo($curlhandle); - This comment for myself)
tcpdump/wireshark ftw.
M
Mario S

Here is a simpler code for the same:

   curl_setopt($ch, CURLOPT_VERBOSE, 1);
   curl_setopt($ch, CURLOPT_STDERR, $fp);

where $fp is a file handle to output errors. For example:

   $fp = fopen(dirname(__FILE__).'/errorlog.txt', 'w');

( Read on http://curl.haxx.se/mail/curlphp-2008-03/0064.html )


I would have liked to use the answer of @Michaël-R- but I didnt get verbose in the PHP log. Logging to a new file like this worked tho.
S
Sir l33tname

Here is an even simplier way, by writing directly to php error output

curl_setopt($curl, CURLOPT_VERBOSE, true);
curl_setopt($curl, CURLOPT_STDERR, fopen('php://stderr', 'w'));

A
Andrew

To just get the info of a CURL request do this:

$response = curl_exec($ch);

$info = curl_getinfo($ch);
var_dump($info);

For "after" response the curl_getinfo its excelent but for malformed urls for example the getinfo returns non info, the opt CURLOPT_VERBOSE its a better for example
N
Nick Spicer

If you just want a very quick way to debug the result:

$ch = curl_init();
curl_exec($ch);
$curl_error = curl_error($ch);
echo "<script>console.log($curl_error);</script>"

S
Serhii Andriichuk

Output debug info to STDERR:

$curlHandler = curl_init();

curl_setopt_array($curlHandler, [
    CURLOPT_URL => 'https://postman-echo.com/get?foo=bar',
    CURLOPT_RETURNTRANSFER => true,

    /**
     * Specify debug option
     */
    CURLOPT_VERBOSE => true,
]);

curl_exec($curlHandler);

curl_close($curlHandler);

Output debug info to file:

$curlHandler = curl_init();

curl_setopt_array($curlHandler, [
    CURLOPT_URL => 'https://postman-echo.com/get?foo=bar',
    CURLOPT_RETURNTRANSFER => true,

    /**
     * Specify debug option.
     */
    CURLOPT_VERBOSE => true,

    /**
     * Specify log file.
     * Make sure that the folder is writable.
     */
    CURLOPT_STDERR => fopen('./curl.log', 'w+'),
]);

curl_exec($curlHandler);

curl_close($curlHandler);

See https://github.com/andriichuk/php-curl-cookbook#debug-request


m
mario

Another (crude) option is to utilize netcat for dumping the full request:

nc -l -p 8000 -w 3 | tee curldbg.txt

And of course sending the failing request to it:

curl_setup(CURLOPT_URL, "http://localhost/testytest");

Notably that will always hang+fail, since netcat won't ever construct a valid HTTP response. It's really just for inspecting what really got sent. The better option, of course, is using a http request debugging service.