111

I am having problems calling a url from PHP code. I need to call a service using a query string from my PHP code. If I type the url into a browser, it works ok, but if I use file-get-contents() to make the call, I get:

Warning: file-get-contents(http://.... ) failed to open stream: HTTP request failed! HTTP/1.1 202 Accepted in ...

The code I am using is:

$query=file_get_contents('http://###.##.##.##/mp/get?mpsrc=http://mybucket.s3.amazonaws.com/11111.mpg&mpaction=convert format=flv');
echo($query);

Like I said - call from the browser and it works fine. Any suggestions?

I have also tried with another url such as:

$query=file_get_contents('http://www.youtube.com/watch?v=XiFrfeJ8dKM');

This works fine... could it be that the url I need to call has a second http:// in it?

Vic Seedoubleyew
  • 9,888
  • 6
  • 55
  • 76
undefined
  • 5,190
  • 11
  • 56
  • 90

16 Answers16

126

Try using cURL.

<?php

$curl_handle=curl_init();
curl_setopt($curl_handle, CURLOPT_URL,'http://###.##.##.##/mp/get?mpsrc=http://mybucket.s3.amazonaws.com/11111.mpg&mpaction=convert format=flv');
curl_setopt($curl_handle, CURLOPT_CONNECTTIMEOUT, 2);
curl_setopt($curl_handle, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl_handle, CURLOPT_USERAGENT, 'Your application name');
$query = curl_exec($curl_handle);
curl_close($curl_handle);

?>
James Hall
  • 7,507
  • 2
  • 22
  • 15
33

Could this be your problem?

Note: If you're opening a URI with special characters, such as spaces, you need to encode the URI with urlencode().

SilentGhost
  • 307,395
  • 66
  • 306
  • 293
23
<?php

$lurl=get_fcontent("http://ip2.cc/?api=cname&ip=84.228.229.81");
echo"cid:".$lurl[0]."<BR>";


function get_fcontent( $url,  $javascript_loop = 0, $timeout = 5 ) {
    $url = str_replace( "&amp;", "&", urldecode(trim($url)) );

    $cookie = tempnam ("/tmp", "CURLCOOKIE");
    $ch = curl_init();
    curl_setopt( $ch, CURLOPT_USERAGENT, "Mozilla/5.0 (Windows; U; Windows NT 5.1; rv:1.7.3) Gecko/20041001 Firefox/0.10.1" );
    curl_setopt( $ch, CURLOPT_URL, $url );
    curl_setopt( $ch, CURLOPT_COOKIEJAR, $cookie );
    curl_setopt( $ch, CURLOPT_FOLLOWLOCATION, true );
    curl_setopt( $ch, CURLOPT_ENCODING, "" );
    curl_setopt( $ch, CURLOPT_RETURNTRANSFER, true );
    curl_setopt( $ch, CURLOPT_AUTOREFERER, true );
    curl_setopt( $ch, CURLOPT_SSL_VERIFYPEER, false );    # required for https urls
    curl_setopt( $ch, CURLOPT_CONNECTTIMEOUT, $timeout );
    curl_setopt( $ch, CURLOPT_TIMEOUT, $timeout );
    curl_setopt( $ch, CURLOPT_MAXREDIRS, 10 );
    $content = curl_exec( $ch );
    $response = curl_getinfo( $ch );
    curl_close ( $ch );

    if ($response['http_code'] == 301 || $response['http_code'] == 302) {
        ini_set("user_agent", "Mozilla/5.0 (Windows; U; Windows NT 5.1; rv:1.7.3) Gecko/20041001 Firefox/0.10.1");

        if ( $headers = get_headers($response['url']) ) {
            foreach( $headers as $value ) {
                if ( substr( strtolower($value), 0, 9 ) == "location:" )
                    return get_url( trim( substr( $value, 9, strlen($value) ) ) );
            }
        }
    }

    if (    ( preg_match("/>[[:space:]]+window\.location\.replace\('(.*)'\)/i", $content, $value) || preg_match("/>[[:space:]]+window\.location\=\"(.*)\"/i", $content, $value) ) && $javascript_loop < 5) {
        return get_url( $value[1], $javascript_loop+1 );
    } else {
        return array( $content, $response );
    }
}


?>
crmpicco
  • 16,605
  • 26
  • 134
  • 210
pangeli
  • 255
  • 2
  • 2
  • 7
    Thanks for the code, looks like you got it from: http://php.net/manual/en/ref.curl.php The main problem is the function call `get_url` should actually be `get_fcontent` since you changed the name of the function itself. This is actually a recursive function call that re-attempts to get the URL contents by changing some parameters. – SSH This Mar 01 '13 at 18:08
  • you got it! was trying to https and was getting turned down. you nailed it. UPVOTED ;) – tony gil Jun 28 '14 at 22:39
22

file_get_contents() utilizes the fopen() wrappers, therefore it is restricted from accessing URLs through the allow_url_fopen option within php.ini.

You will either need to alter your php.ini to turn this option on or use an alternative method, namely cURL - by far the most popular and, to be honest, standard way to accomplish what you are trying to do.

Michael Wales
  • 10,360
  • 8
  • 28
  • 28
  • Nevermind, just noticed he said `file_get_contents()` worked on a different URL. Nonetheless, this is still a good tip for others having this issue. – Michael Wales Mar 30 '09 at 14:44
  • yes, Ive looked at other options and see that cURL is the standard way to go but I tried this as it was easier and worked with other urls, I think i have to restart apache to intsall cURL? and cant figure out how to do this (another question)... thanks for your quick response – undefined Mar 30 '09 at 14:49
18

You basically are required to send some information with the request.

Try this,

$opts = array('http'=>array('header' => "User-Agent:MyAgent/1.0\r\n")); 
//Basically adding headers to the request
$context = stream_context_create($opts);
$html = file_get_contents($url,false,$context);
$html = htmlspecialchars($html);

This worked out for me

d_bhatnagar
  • 1,419
  • 1
  • 12
  • 20
  • 2
    This worked for me too! Looks like it needed a user agent – bryan Dec 16 '17 at 20:53
  • If the url seems properly encoded, this could very well be the issue. Some site will restrict upon 'User-Agent', perhaps 'Accept' as well. – James John McGuire 'Jahmic' Apr 14 '20 at 08:12
  • 2
    super answer. vote for promote this one to the top. all in php and worked for https request too. just two extra lines code. what if shared server do provide curl? this is very helpful. – ndasusers Jun 03 '20 at 18:22
14

I notice that your URL has spaces in it. I think that usually is a bad thing. Try encoding the URL with

$my_url = urlencode("my url");

and then calling

file_get_contents($my_url);

and see if you have better luck.

acme
  • 14,654
  • 7
  • 75
  • 109
slim
  • 2,545
  • 1
  • 24
  • 38
6

I got a similar problem.

Due to timeout !

Timeout can be indicated like this :

$options = array(
    'http' => array(
        'header'  => "Content-type: application/x-www-form-urlencoded\r\n",
        'method'  => "POST",
        'content' => http_build_query($data2),
        'timeout' => 30,
    ),
);
$context = stream_context_create($options);
$retour = @file_get_contents("http://xxxxx.xxx/xxxx", false, $context);
Jerry
  • 1,141
  • 1
  • 13
  • 18
4

I got a similar problem , I parsed the youtube url. The code is;

$json_is = "http://gdata.youtube.com/feeds/api/videos?q=".$this->video_url."&max-results=1&alt=json";
$video_info = json_decode ( file_get_contents ( $json_is ), true );     
$video_title = is_array ( $video_info ) ? $video_info ['feed'] ['entry'] [0] ['title'] ['$t'] : '';

Then I realise that $this->video_url include the whitespace. I solved that using trim($this->video_url).

Maybe it will help you . Good Luck

Alfred
  • 21,058
  • 61
  • 167
  • 249
Emre Karataşoğlu
  • 1,649
  • 1
  • 16
  • 25
2
$query=file_get_contents('http://###.##.##.##/mp/get?' . http_build_query(array('mpsrc' => 'http://mybucket.s3.amazonaws.com/11111.mpg&mpaction=convert format=flv')));
Sergey
  • 21
  • 1
2

I'm not sure about the parameters(mpaction, format), if they are specified for the amazonaws page or ##.##.

Try to urlencode() the url.

alexn
  • 57,867
  • 14
  • 111
  • 145
  • thanks - these are params for the mediaplug instance. If I urlencode the url it still does not work - I get a very garbled url in the error... ?? – undefined Mar 30 '09 at 14:42
  • You should be encoding only the parameter string: "convert format" should be "convert%20format" (or alternatively "convert+format"). – bobince Mar 30 '09 at 15:03
2

This function solved my problem

function file_get_contents_curl($url) {
$ch = curl_init();
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); //Set curl to return the data instead of printing it to the browser.
curl_setopt($ch, CURLOPT_URL, $url);
$data = curl_exec($ch);
curl_close($ch);
return $data;
}
  • 1
    Your answer could be improved with additional supporting information. Please [edit] to add further details, such as citations or documentation, so that others can confirm that your answer is correct. You can find more information on how to write good answers [in the help center](/help/how-to-answer). – Community Dec 18 '22 at 14:18
  • Thank you, it worked just fine for me.:) – user2812532 Jan 18 '23 at 17:53
1

This wasn't working for me and I was getting a null value for the result query. So I checked on postman to see if the api was actually returning values and it was. Post man has this tab on the right where you can get sample code that was used to get the results and after trying that it finally worked, but initially you might get a weird error 411 saying the post length needs to be specified I added the fix in my code below. To bypass the 411 POST length error create an empty array and use the http_build_query function. Then set that variable in the CURLOPT_POSTFIELDS curl option.

$data_string = array();
$curl = curl_init();
$test = http_build_query($data_string);
curl_setopt_array($curl, array(
CURLOPT_URL => 'https://www.googleapis.com/geolocation/v1/geolocate?key=APIKEY',
CURLOPT_POSTFIELDS => $test,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => '',
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 0,
CURLOPT_FOLLOWLOCATION => true,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => 'POST',
));

$response = curl_exec($curl);

curl_close($curl);
echo $response;
0

This is what worked for me... I did not use curl.

I was able to access a particular API url via browser, but when used in file_get_contents, it gave the error " failed to open stream".

Then, I modified the API URL that I wanted to call by encoding all double quotes with urlencoding and kept everything else untouched.

Sample format is given below:

$url = 'https://stackoverflow.com/questions'.urlencode('"'.$variable1.'"');

Then use

file_get_contents($url);

Soumya Rajiv
  • 87
  • 1
  • 4
0

Had same issue but it was a firewall issue... once I had the API server whitelisted, it worked fine, using both get_file_contents($url) and the curl method above...

hours wasted before discovering the firewall rule issue.

0

For me the problem was an incorrect value in the Content-Length header. The value was too great, so nginx kept waiting for the rest of the content that never arrived.

mae
  • 14,947
  • 8
  • 32
  • 47
-5

Use this

file_get_contents($my_url,null,null);
josliber
  • 43,891
  • 12
  • 98
  • 133