I'm having a problem with .htaccess file rewrite rules. I want to have one .htaccess file in my root directory and to have rule over there to stop people to be able to access files directly over browser. So, for example I have folder blah/includes/file.php and .htaccess file is in blah/ folder, I want to prevent people to be able to just type in browser blah/includes/file.php and get that file, but also I want my functions in app to be able to use those files. I understand that is almost impossible for them to know exact name of my include files but I would like to be sure.
Thanks in advance.
here is my code which is not responding:
<IfModule mod_rewrite.c>
## Enable Mod Rewrite, this is only required once in each .htaccess file
RewriteEngine On
RewriteBase /
## Test for access to includes directory
RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /includes/ .*$ [NC]
## Test that file requested has php extension
RewriteCond %{REQUEST_FILENAME} ^.+\.php$
## Forbid Access
RewriteRule .* - [F,NS,L]
</IfModule>
Note: I'm testing in localhost if that is maybe important.
Problem is in the first RewriteCond you have a space after /includes/, which throws an error.
BUT: I wouldn't use %{THE_REQUEST}, as it contains the HTTP Request (see http://httpd.apache.org/docs/2.2/mod/mod_rewrite.html#rewritecond). Use %{REQUEST_URI} instead.
So, if you want to forbid access to /<folder>/include/*.php, you can use just this code:
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteCond %{REQUEST_URI} ^/[^/]+/includes/.*\.php$ [NC]
RewriteRule .* - [F,NS,L]
</IfModule>
Assuming your .htaccess lies in the blah/ folder.
The quickest way would be just to put a one-line .htaccess file in your includes directory:
deny from all
The other alternative is to place your includes folder outside of your web-accessible directory.
/home/
/username/
/includes/
/public_html/
/index.php
If you still want to use a RewriteRule, then this is the one you’d use:
RewriteRule ^includes/ - [F,L,NC]
Which would return a 401 Forbidden response trying to access a URI that begin with includes.
Related
I feel like this is a rather common request, but I am too confused about .htaccess and couldn't find a solution by Google.
I have a Laravel instance in a subdirectory of the Apache2 htdocs. Now I would like to invisibly redirect all requests from the root domain to this folder (it should be the "root" website). But the tricky thing is, this is not the only folder, there are other folders directly in the htdocs, which should be reached normally. Just the "root" website is not in the root but also in a subfolder. For example:
https://domainA.com should load https://domainA.com/laravel/public (including possible query string or parameters, but invisibly for the user)
https://domainA.com/websiteB should be served as it is
https://domainA.com/websiteC should be served as it is
...
I assume, part of this solution will be to list all the websiteB, websiteC directories in the .htaccess, would it be possible to automate this?
Thanks in advance!
You can put a .htaccess in the folder you want to custom controle but you have to create some filter condition
<IfModule mod_rewrite.c>
RewriteEngine On
## RewriteBase /foo
## conditions to tell what to redirect ie on URI
## RewriteCond %{REQUEST_URI} ^/a-folder/
## not websiteB or websiteC
RewriteCond %{REQUEST_URI} !^/websiteB/
RewriteCond %{REQUEST_URI} !^/websiteC/
## if the file does not exist call index.php
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ my/path/to/a/script.php [L]
</IfModule>
After you have to do something special in script.php for those HTTP calls
You can also rewrite the URI and pass it again to apache but things can be complicated after...
Note: This question has been asked before several times, but the answers are really bad, totally wrong and/or do not fit the above scenario (because there are several files called index.php). If you like, see [1].
I want to block direct access to all .php files in the application folder (see file structure image) via the .htaccess file in the root folder. There are some solutions for this on the web, but they miss one thing: They don't work if there is more than one file named index.php (which is a realistic scenario like the screenshot shows, see the file in the view/xxx/ folder):
Question: How to block access to all .php files, except the index.php in the root folder ?
In .htaccess:
RewriteEngine on
RewriteRule ^/application - [F]
The [F] option instructs it to issue a 403 Forbidden response on all matching URLs.
Or add a separate .htaccess file in /application containing just:
deny from all
Or in your Apache vhost definition:
<Location /application>
deny from all
</Location>
In addition to Niels Keurentjes excellent answer I would like to extend his solution according to my .htacces that uses some very common rewriting patterns (as a lot of people might run into the same problem):
When using URL rewrite rules, then the line RewriteRule ^/application - [F] has to be at exactly that place. It will not work if the line is placed before or below:
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-l
# The new line, blocking direct access to every file in /application and deeper
RewriteRule ^/application - [F]
RewriteRule ^(.+)$ index.php?url=$1 [QSA,L]
how can I show folder name instead of file name?
For example,
www.example.com/home/index.php -> www.example.com/home
I know when I browse www.example.com/home I will get the result but that is not what I want because it will add a / behind the folder name (e.g www.example.com/home/).
What I want is without the / behind the folder and when user browse www.example.com/home/index.php the page will redirect the user to page not found. The purpose I do this is to hide the language I used and make the link more readable and memorable.
I found something like rewrite the rules in .htaccess file but I am new in php so I don't how to make it. Anyone can give me suggestion or provides some tutorial about this.
Thanks.
To remove the slash, you must first disable DirectorySlash
DirectorySlash Off
DirectoryIndex disabled
Direct access to PHP files can be answered with a R=404 status code
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteRule \.php$ - [R=404,L]
And then, you can rewrite requests pointing to a directory and containing an index.php
RewriteCond %{REQUEST_FILENAME}/index.php -f
RewriteRule ^.*$ /$0/index.php [L]
This RewriteCond looks, if the requested URL is a directory and if there is an index.php in this directory. If this is the case, then the index.php is executed.
Putting all together
DirectorySlash Off
DirectoryIndex disabled
RewriteEngine on
# prevent direct access to PHP files
RewriteCond %{ENV:REDIRECT_STATUS} ^$
RewriteRule \.php$ - [R=404,L]
# rewrite requests for a directory to index.php
RewriteCond %{REQUEST_FILENAME}/index.php -f
RewriteRule ^.*$ /$0/index.php [L]
Htaccess doesn't have anything common with PHP. Htaccess is Apache's configuration file, so you need to play with htaccess to achieve that what you want. On the other hand your solution will be really dirty. Learn about MVC and FrontController to make your structure cleaner.
What rule should i set, to make the mod_rewrite ignore the directory "public" completely?
By that, I mean, the files should be accessible within it, but if the file does not exist, a server error page should come up with something like, FORBIDDEN, or FILE NOT FOUND what ever. I do not need custom error pages or stuff like that. I simply want the "public" to behave like there is no mod_rewrite at all.
Here is my .htaccess file:
RewriteEngine on
RewriteCond $1 !^(index\.php|robots\.txt)
RewriteRule ^(.*)$ index.php/$1 [L,QSA]
My file structure is
/system/
/application/
/public/
I want the folder public to behave, like there are no rewrite rules set at all, completely ignore it.
edit
That's my .htaccess file:
RewriteEngine on
RewriteRule ^(public)($|/) - [L,NC]
RewriteCond $1 !^(index\.php|robots\.txt)
RewriteRule ^(.*)$ index.php/$1 [L,QSA]
I already had this .htaccess in the /public/ folder:
RewriteEngine off
I've tried all the different answers above (and a ton from google). I've tried to mix 'em up what so ever.
My folders:
/system/
/application/
/public/
/public/.htaccess #RewriteEngine off
/public/favicon.ico
/index.php
Below are the url with results I'm getting:
/public/favicon.ico -> I get the favicon
/public/faviDon.ico -> I get the index.php (without mod rewrite you would get "not found")
/public/ -> I get the index.php (without mod rewrite "forbidden")
So it still does rewrite urls, if the file was not found, or upon accessing a folder directly.
Can you se it?
Thank you very much for effort guys! I really appreciate it!
EDIT
I completely setup your files on my machine
// /.htaccess
RewriteEngine on
RewriteRule ^(public)($|/) - [L,NC]
RewriteCond $1 !^(index\.php|robots\.txt)
RewriteRule ^(.*)$ index.php/$1 [L,QSA]
.htaccess in the public folder:
// /public/.htaccess
Options -Indexes
RewriteEngine off
This disables rewriting like you wanted.
/public/ -> 403 Forbidden
/public/favicon.ico -> 200 File found
/public/not-existing.ext -> 404 File not found
Do you have a index.php in you public folder?
Maybe you could remove that one..
What kind of machine your testing on?
I tested it on Linux + Apache 2 + PHP5.3
I can give you more support in the afternoon (my time +2 GMT)
EDIT 2
When I remove this line from /.htaccess is still works
RewriteRule ^(public)($|/) - [L,NC]
Everything is handled by the .htaccess in the public folder.
Maybe it's a caching problem in your browser. Try a different browser/clean up history/install app to remove cache.. (depending on what browser you're using)
I have nearly 30 php files, 4 sub directories in my directory. I want to block some php files and sub directories from user in direct viewing like http://bhavani.com/hai.php
My currect htaccess file
## Enable Mod Rewrite, this is only required once in each .htaccess file
RewriteEngine On
RewriteBase /
## Test for access to includes directory
RewriteCond %{THE_REQUEST} ^[A-Z]{3,9}\ /includes/ .*$ [NC]
## Test that file requested has php extension
RewriteCond %{REQUEST_FILENAME} ^.+\.php$
## Forbid Access
RewriteRule .* - [F,NS,L]
How to do it?
You can filter the files like this
<Files ~ "\.php$">
Deny from all
</Files>
And directory like this
<Directory "/subdirectory">
Deny from all
</Directory>
You don't need mod_rewrite to accomplish this. A much simpler way of doing this would be with RedirectMatch directive from mod_alias:
RedirectMatch 403 ^.*/include/*\.php$
This will automatically respond with 403 Forbidden to a direct request for any PHP file inside include subdirectory, however you would still be able to include them from inside other php files.
I think you can use only RewriteRule without RewriteCond
For example:
RewriteRule ^/hai\.php - [F, NS, L]
This rule forbid access to file hai.php
For other files you can use other Rule or use mask.