I want to disallow access to all files and folders in protected directory on my server.
I have used this in .htaccess
file in that directory:
Deny from all
But the problem is I also want to use curl from another website to query one file in this directory:
$curl = curl_init();
$post_data = array();
$post_data['token'] = $token;
curl_setopt($curl, CURLOPT_POST, true);
$url = 'https://my-website.com/protected-dir/file.php';
curl_setopt($curl, CURLOPT_URL, $url );
$response = curl_exec($curl);
if (curl_errno($curl)) {
return(curl_errno($curl));
} else{
return $response;
}
curl_close($curl);
Now I get error 22 from CURL. I want to protect direct access to all files and folders in that directory. What are my options?
I can place this directory outside of web root, but how would I use CURL then? (what is the URL to that file?)
other solutions?
CodePudding user response:
The easy answer is to leave the file inside the document root and then just add an allow
exception to the .htaccess
file, which lists the IP address of the remote server you want to allow hits from:
allow from 1.2.3.4
deny from all
But note this will allow any user on that machine to grab the file. The secure answer is to always put sensitive content outside the document root and never rely on .htaccess to protect you. Then create an authenticated proxy page for any exceptions.
public/
index.php
secret.php
private/
secret_file
Where public
is the document root, index.php
is your regular site, and secret.php
would be something like:
// run some checks to ensure that you're allowed to do this:
// maybe check source IP
// maybe check for a username and password
// maybe check for a specific bearer token in a header
header('Content-Type: whatever');
readfile('/path/to/private/secret_file');
CodePudding user response:
It would seem (from comments) that this code is part of a WordPress plugin that can potentially be installed on any website. In which case this file needs to be "public".
The file shouldn't be in the protected directory to begin with. However, you can block everything except the file in question using a <FilesMatch>
container and a regex/negative lookahead.
For example:
<FilesMatch "^(?!file\.php$).*">
Require all denied
</FilesMatch>
Everything is blocked except for requests to file.php
. Note that the Deny
directive is formerly deprecated and you should be using the corresponding Require
directive instead on Apache 2.4 . (But note that you should not mix both old and new authentication directives.)
I assuming that your script contains the usual validation, for example:
- fails early on any non-POST request.
- fails on any POST request that does not contain a suitable
token
parameter. - enforces a "delay" on any failed token requests to prevent brute force attacks.
You could also set a custom User-Agent string as part of the CURL (POST) request and check for this in your script or earlier in .htaccess
- but that's just smoke and mirrors and doesn't really offer any additional "protection".