08 April 2008

fopen($url) v. curl in PHP

Occasionally you'll see PHP code which uses require() or include() or fopen() or file_get_contents() to import code from a remote location (the argument to those functions can be a URL). This sort of thing is generally considered to be a bad security practice, especially if you don't control the code at the remote location (it could unexpectedly change in such a way as to do something destructive to your application).

Many PHP security experts tend to recommend disabling the allow_url_fopen option in php.ini. Disabling this feature can even serve to prevent inadvertent code injection. Imagine an application which calls require($file) where $file is dynamically determined. If your application has some sort of problem which allows an attacker to set the value of $file, the attacker can inject the code of his/her choosing into your application.

So I feel that disabling allow_url_fopen is a good idea, but sometimes you need to initiate HTTP requests in your PHP code. The curl extension provides a good way of doing this. The following snippet will put the contents of the Web page at $url into the $page variable:

$ch = curl_init($url);
curl_setopt( $ch, CURLOPT_RETURNTRANSFER, 1 );
curl_setopt( $ch, CURLOPT_HEADER, 0 );
$page = curl_exec($ch);
curl_close($ch);


The previous example is a GET request, but you can also do POST:

$postdata = 'var1=value1&var2=value2';
$ch = curl_init($url);
curl_setopt( $ch, CURLOPT_RETURNTRANSFER, 1 );
curl_setopt( $ch, CURLOPT_HEADER, 0 );
curl_setopt( $ch, CURLOPT_POSTFIELDS, $postdata );
$page = curl_exec($ch);
curl_close($ch);

1 comment:

Anonymous said...

I ran into the allow_url_fopen PHP security problems and had to rewrite fopen by using cURL for my Image Cache Function Script. The code might help someone understand the differences.