I'll trying to figure out how to protect directory from unauthorized or not autentificated user to download files.
Thank's in advance.
Can't find a good duplicate, but a little search will bring up results like this PHP protect a folder
There is a simple way to restrict folder access based on PHP session authorization using php. It requires creating stub files for valid authorized sesssions (and automating their deletion). In PHP you do:
if ($user_has_permission_to_download)
{
touch("tmp/access-" . session_id());
}
Then a simple rewriterule+rewritecond can then serve for authorization:
RewriteCond %{HTTP_COOKIE} PHPSESSID=(\w+)
RewriteCond ../tmp/access-%1 -f
RewriteRule ^(.+)$ $1 [L]
RewriteRule .+ /deny [L]
The first block permits access when the according cookie value is found and an authorization stub file exists. The second rule blocks access for anyone else.
Put a .htaccess file in the directory with the files, with the following content
deny from all
Then create a script that that uses for instance readfile() to serve the file if the user is authorized.
I'm assuming you have a users / login script somewhere that authenticates a user?
Use .htaccess rewrite rules to forward the file request through a php script that checks a session variable if the user is logged in then returns the file.
Something of the elk:
.htaccess
RewriteEngine on
RewriteRule ^(.*).(pdf|exe|doc|whatever)$ some-script.php?file=$1.$2 [L]
<?php
if(loginCheck()) //function somewhere that checks session if user is logged in
{
return fopen('../files/' . $_GET['file']); //open and return the requested file
}
This is just pseudo code to give you an idea of what you need to do. You may also have to echo the correct file headers as well.
And to stop people from just going to the files directory, I recommend putting an .htaccess file in THAT folder as well saying deny from all to stop EVERYONE from accessing it.
.htaccess is your best friend. Put deny from all into that .htaccess file. Or if you don't want to use .htaccess file encrypt and change all the time the download path (LOL!).
Related
I'm trying to restrict access to all files in a folder.
I have to check if the user is authenticated and some other verifications. So I have to check it in a PHP file.
But I think I have to pass by a .htaccess file, that should check if the user want to access to a file in some specifics folder and then redirect to my "filehandler.php" file.
I want to restrict access to all files in a "documents/private/" folder and its subfolders.
Then I tried this (.htaccess):
RewriteEngine on
RewriteBase /
RewriteCond %{REQUEST_URI} ^\/(private/|dummy)\/.*$
RewriteRule !^((.*.html)|(.*\/))$ filehandler.php
But it doesn't redirect to the "filehandler.php" file.
Can someone help me ? Thanks in advance
PS: I found lots of explanations about it, but as I don't know the syntax at all, I didn't succeed to make what I want to do.
I would like to check if users are logged in to access image files.
Images would have this form
https://domain.com/folders/imagename.jpg
I tried this in the .htaccess:
RewriteEngine On
RewriteCond %{REQUEST_URI}\.jpg
RewriteRule ^(.*)\.jpg$ /protect.php
And this in my protect.php file
<?php
if(rcp_is_active()){
header('Content-Type: image/jpg');
readfile($imageurl);
}
else{
readfile("https://placeholdit.imgix.net/~text?txtsize=38&txt=Forbidden&w=400&h=400")
}
?>
My question:
How should I complete my .htaccess file to pass the filename.jpg to the php file?
Update your .htaccess RewriteRule to pass the matched filename to the PHP script as follows (your RewriteCondition is superfluous):
RewriteEngine On
RewriteRule ^((.*)\.jpg)$ /protect.php/$1
Then you can access the passes value using $_SERVER['PATH_INFO'] or $_SERVER['PATH_TRANSLATED'] (then Apache tries to map it to the real path according to document root, see mod_cgi and RFC 3875 for more information about this). For this to work AcceptPathInfo needs to be enabled in Apache httpd (the default).
or use
RewriteRule ^((.*)\.jpg)$ /protect.php?filename=$1
and use $_GET['filename']. Especially here, beware for directory traversal attacks (e.g., someone uses /protect.php?filename=../../someother-file.jpg). I usually apply realpath to normalize the path and check that it starts with the folder which contains the files or the document root ($_SERVER['DOCUMENT_ROOT']).
In both cases also make sure you only deliver allowed files (e.g., what happens if an attacker uses /protect.php/protect.php). This might leak sensitive data.
PS: Maybe you also want to make the response non-cacheable or provide a Content-Length.
PSS: Even for the forbidden case you also need to provide a proper Content-Type - or use a redirect (header('Status: 302'); and header("Location: https://placeholdit.imgix.net/~text?txtsize=38&txt=Forbidden&w=400&h=400");) so that you don't need to re-request that image again and again.
I have just written some PHP code to combine all the JS on my website into a single file, hash it, then echo out the <script> tag with the hashed filename as the source. I store all these hashed files in a single folder, and delete old hashes every time a new hash is generated.
I want to be able to turn on caching for this file, as the hashed filename determines when the browser needs to download a new file (IE: The actual URL that it requests is different). Does anyone know how to hook into this request in PHP? Something like:
if ($_GET['folder'] = "path/to/hashed/folder/or/file")
{
//Do something
}
Any help is greatly appreciated.
Unless you are serving your JavaScript with PHP, you can't hook into the request. However, you don't need to set caching headers with PHP. You can configure your web server to do this directly. How you do this depends on what server you are using.
What you are going to use for this is a file called .htaccess. Here is a simple rule that sends everything through one file, here named index.php.
RewriteEngine on
RewriteBase /
RewriteCond %{REQUEST_URI} !^/some_file_that_you_want_to_exclude_from_this_rule
RewriteCond %{REQUEST_URI} !^/some_other_file_that_you_want_to_exclude_from_this_rule
RewriteRule ^(.*)$ index.php [L]
The full URL will be in $_SERVER['REQUEST_URI'], and other variables in $_SERVER will point you to other information ($_SERVER['REDIRECT_URL'] excludes the host name).
I have a protected folder. I want people who are logged in (via PHP / WordPress) to have access to the folder and the files therein.
Those who are not logged in should be redirected via .htaccess.
Can the .htaccess rewrite condition be based off an environment variable or a server variable which I added or edited from PHP?
UPDATE:
See my answer below.
.htaccess (hypertext access) file is a directory-level configuration file supported by several web servers. I can't think of any simple way of how you could access runtime variables set in PHP with .htaccess as .htaccess allows no "execution" of commands, it is just a bunch of config directives.
You could maybe do some sort of VERY VERY strange combination of .htaccess and CGI scripts and maybe more to access a webservice # PHP level, but that would be far beyond my programming skills and I suppose beyond those of most PHP developers too...
At least this is what I can tell you, I would be interestd too if someone knows a hack for this...
The easiest way of how to do such redirects would in my opinion be header("Location: xxx.html"); directly in PHP.
You can't edit the .htaccess file on the fly using PHP to set these variables. I mean, you can, but the .htaccess file is used by the entire server, not per-user. Unless you wanted to do some ridiculous write-username-environment-variables to .htaccess and hope it works somehow, you're much better off just doing this via php. If they're not logged in, you can redirect them away with PHP so they won't be able to see the protected folders either.
If you want to keep them out of an entire folder but you don't want to do something like require security-check.php on every file, you could look into using auto_prepend_file. You could also use your .htaccess to route all file access through one specific php file that does this. You would need to do this if you were keeping people out of non-php files.
After much research, I solved it.
My folder system is setup like this:
/file-share/users-folder-name
My .htaccess file under /file-share is as follows:
# .htaccess /file-share
RewriteEngine On
RewriteBase /
# no cookie set
RewriteCond %{HTTP_COOKIE} !^.*client.*$ [NC]
RewriteRule ^(.*)$ /file-share-redirect.php?q=$1 [NC,L]
# cookie set
RewriteCond %{QUERY_STRING} !verified$ [NC]
RewriteCond %{HTTP_COOKIE} client=([^;]+) [NC]
RewriteRule ^(.*)$ /file-share/%1/$1?verified [NC,L,QSA]
# custom 404
ErrorDocument 404 /file-share-redirect.php?e=404&q=$1
#end
If the cookie is set and the file exists in the client's folder then the client is redirected seamlessly to the requested file. The final file request is also given a url parameter to avoid a loop in redirection.
If a user is logged but the cookie is not set I have my file-share-redirect.php file create the cookie then redirect to the requested file. The cookie created in the code below is set to expire in an hour.
<?php setcookie('client', $users_folder_name, time()+3600); ?>
UPDATE
You can keep the cookie secure by using an encrypted cookie name and value. The cookie will only be created on systems where users log in.
PHP's setcookie() will even let you create a cookie that is inaccessible from JavaScript. I double checked this.
The subfolder names will be quite complex, completely unguessable. No one will ever see the subfolder names except those with ftp access. Even those logged in will only see /_/filename.ext, without the subfolder.
In my website, i want to restrict viewing certain files which are stored in a directory called "/content" such that only logged in users can view the files
as it stands right now anyone who types in xxxxxxx.com/content/4dc32b1c0a630.png into the browser can see this image file
I've added Options -Indexes to my .htaccess file but that didn't do anything
if it is helpful my site is built using codeigniter, so a PHP solution would be great, though I'd take any advice you might have!
thank you,
Tim
You can write a controller for that purpose.
In one of my projects I've done a resized pictures controller only for logged in users. It's based on timthumb script http://code.google.com/p/timthumb/
In controller __contruct(); write user authentification code and that's all!
So you will call these files via controller, like http://www.site.com/images/1314.png
Use mod_rewrite to rewrite any accesses to anything in /content to a PHP script that will auth the user and then provide the file, either directly or via mod_xsendfile.
Put these lines in your root .htacess file to block access to content/4dc32b1c0a630.png for unauthenticated users:
Options +FollowSymlinks -MultiViews
RewriteEngine on
RewriteCond %{LA-U:REMOTE_USER} ^$
RewriteRule ^content/4dc32b1c0a630\.png/?$ - [R=403,L]
However I would suggest you use wild cards (if possible) to match blocked files above rather than listing each and every individual file.