|
php.net | support | documentation | report a bug | advanced search | search howto | statistics | random bug | login |
[2007-12-01 10:00 UTC] peter at petersmit dot eu
Description:
------------
If you use a php://memory stream in combination with curl, nothing is written to the stream.
A filestream works fine.
Reproduce code:
---------------
<?php
$c = curl_init("http://example.com");
$st = fopen("php://memory", "r+");
curl_setopt($c, CURLOPT_FILE, $st);
if(!curl_exec($c)) die ("error: ".curl_error($c));
rewind($st);
echo "Content|".htmlspecialchars(stream_get_contents($st))."|/Content";
fclose($st);
?>
Expected result:
----------------
Content|The content of example.org|/Content
Actual result:
--------------
Content||/Content
PatchesPull RequestsHistoryAllCommentsChangesGit/SVN commits
|
|||||||||||||||||||||||||||||||||||||
Copyright © 2001-2025 The PHP GroupAll rights reserved. |
Last updated: Sun Oct 26 03:00:01 2025 UTC |
i have discovered that this does work, partially, for some urls. im not sure what is preventing this from working on all urls, but even for ones where it does work, the entire result is not placed in the buffer. here is a modification of peters code, which illustrates 2 urls that work partially, one is the google translate 'api', the other is php.net. <?php #$c = curl_init("http://example.com"); #$c = curl_init("http://google.com/translate_t?langpair=en%7Cfr&text=newspaper"); $c = curl_init("http://php.net"); $st = fopen('php://memory', 'r'); curl_setopt($c, CURLOPT_FILE, $st); curl_setopt($c, CURLOPT_USERAGENT, 'Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.8.1.11) Gecko/20080115 Firefox/2.0.0.11'); if(!curl_exec($c)) die ("error: ".curl_error($c)); curl_close($c); rewind($st); /* $str = fgets($st); var_dump($str); */ echo stream_get_contents($st); #echo "Content|".htmlspecialchars(stream_get_contents($st))."|/Content"; fclose($st); ?>Well, I just discovered that I can use fstat to get the size of a stream (even memory ones). Follows the test case: $fi = fopen('php://temp', 'rb+'); // fill the $fi stream with some data $input_stat = fstat($fi); $input_size = $input_stat['size']; curl_setopt($ch, CURLOPT_PUT, true); curl_setopt($ch, CURLOPT_INFILE, $fi); curl_setopt($ch, CURLOPT_INFILESIZE, $input_size); curl_exec($ch); DaviThe final workaround I currently use is setting both CURLOPT_WRITEFUNCTION and CURLOPT_READFUNCTION options. So I can write and read using the memory stream, even being unsupported by CURL: // open the memory stream (currently using "temp" but it should works with "memory" stream as well): $temp = fopen('php://temp', 'rb+'); function cb_curl_write($ch, $data) { global $temp; return fwrite($temp, $data); } function cb_curl_read($ch, $fd, $size) { global $temp; return fread($temp, $size); } // put some data into the stream: // TODO rewind($temp); // get the content size of the stream $input_stat = fstat($temp); $input_size = $input_stat['size']; $ch = curl_init('http://www.php.net/'); curl_setopt($ch, CURLOPT_PUT, true); curl_setopt($ch, CURLOPT_INFILESIZE, $input_size); curl_setopt($ch, CURLOPT_WRITEFUNCTION, 'cb_curl_write'); curl_setopt($ch, CURLOPT_READFUNCTION, 'cb_curl_read'); curl_exec($ch); curl_close($ch);