Remove public folder from URL with htaccess - .htaccess

Is it possible to 'remove' a folder from the URL so if somebody types http://www.example.com/dummy/public/index into their browser address bar, I can strip the 'public' folder, so the URL reads http://www.example.com/dummy/index
I essentially want to hide the 'public' folder so it never appears in the URL.
I have this htaccess at the root of my site which is www.example.com/dummy/
RewriteEngine on
RewriteRule ^(.*) public/$1 [L]
This is the htaccess inside my public folder which is located at www.example.com/dummy/public/
Options -MultiViews
# Activates URL rewriting (like myproject.com/controller/action/1/2/3)
RewriteEngine On
# Prevent people from looking directly into folders
Options -Indexes
# If the following conditions are true, then rewrite the URL:
# If the requested filename is not a directory,
RewriteCond %{REQUEST_FILENAME} !-d
# and if the requested filename is not a regular file that exists,
RewriteCond %{REQUEST_FILENAME} !-f
# and if the requested filename is not a symbolic link,
RewriteCond %{REQUEST_FILENAME} !-l
# then rewrite the URL in the following way:
# Take the whole request filename and provide it as the value of a
# "url" query parameter to index.php. Append any query string from
# the original URL as further query parameters (QSA), and stop
# processing this .htaccess file (L).
RewriteRule ^(.+)$ index.php?url=$1 [QSA,L]
I tried changing the last RewriteRule to RewriteRule ^(.+)public/(.*)$ index.php?url=$1$2 [QSA,L] but when I type www.example.com/dummy/public/index the page loads but the browser address bar still shows 'public' in the path.
Is it possible to do what I'm attempting?
I've seen a few SO answers that claim to accomplish this such as .htaccess: remove public from URL and URL-rewriting with index in a "public" folder, but none of them work for me.

If you want to remove public/ from your URLs then rule should be placed inside /public/.htaccess since all the requests with URI starting with /dummy/public/ will be managed by rules inside /public/.htaccess.
Change your /public/.htaccess with this:
# Prevent people from looking directly into folders
Options -Indexes -MultiViews
# Activates URL rewriting (like myproject.com/controller/action/1/2/3)
RewriteEngine On
# remove public/ from URLs using a redirect rule
RewriteCond %{THE_REQUEST} \s/+(.+/)?public/(\S*) [NC]
RewriteRule ^ /%1%2? [R=301,L,NE]
# If the following conditions are true, then rewrite the URL:
# If the requested filename is not a directory,
RewriteCond %{REQUEST_FILENAME} !-d
# and if the requested filename is not a regular file that exists,
RewriteCond %{REQUEST_FILENAME} !-f
# and if the requested filename is not a symbolic link,
RewriteCond %{REQUEST_FILENAME} !-l
# then rewrite the URL in the following way:
# Take the whole request filename and provide it as the value of a
# "url" query parameter to index.php. Append any query string from
# the original URL as further query parameters (QSA), and stop
# processing this .htaccess file (L).
RewriteRule ^(.+)$ index.php?url=$1 [QSA,L]

Fear not! For the answer is yes. Use the following rule in your .htaccess to remove the /public/ folder from your URLs:
RewriteEngine On
RewriteRule ^(.*)/public /$1 [R=301,L]
This will leave you with the desired URL of http://www.example.com/dummy/index and it achieves this using a 301 permanent redirection. For testing purposes I suggest you change this to 302 as this will make it temporary, once happy, change it back.
Make sure you clear your cache before testing this.

Related

remove file names completely from url with .htaccess

With some modifications is possible to hide extension of the web files like http://www.abc.com/asd/zxc/ against to zxc.php but the thing I wanna do is remove file names completely from the url like http://www.abc.com/asd/ it doesn't matter user where to go in web site but the url should be stay static all the time.
Is it possible to do that with .htaccess?
I already tried this but it didn't work:
RewriteOptions inherit
RewriteEngine On # enables url rewriting
RewriteCond %{REQUEST_FILENAME} !-d # if requested uri is not directory (!-d)
RewriteCond %{REQUEST_FILENAME}\.php -f # and if there is a file named URI+'.php' (-f)
RewriteRule ^(.*)$ $1.php # then if there is any thing in uri then rewrite it as uri+'.php'
I'm not sure, but isn't the problem that you would like to check so the supplied url fragment is not a directory and not a file, and if that's the case, append .php to the fragment?
Something like this might work:
RewriteEngine On # enable mod_rewrite
RewriteBase / # set the 'base' for the rewrite
# you might need to modify this one.
RewriteCond %{REQUEST_FILENAME} !-f # not a file
RewriteCond %{REQUEST_FILENAME} !-d # not a directory
RewriteRule ^(.*)$ /$1\.php [L] # append '.php' to the path
#
If you have the following directory structure, and of course the .htaccess file in the root of the structure:
/code/test.php
/index.php
You should be able to access the test.php and index.php files by using the following urls:
http://example.com/code/test/
and
http://example.com/index/
The example.com needs to be change to a valid domain or ip address.

Root folder change (.htaccess)

In my "public_html" directory I have the following structure:
- root
- index.html
- blog
- index.html
- lab
- index.html
- wp
- (WORDPRESS FILES)
The "lab" and "wp" directories are just subdomain directories ("http://lab.tomblanchard.co.uk" and "http://wp.tomblanchard.co.uk") which work fine.
Basically I want the main domain ("http://tomblanchard.co.uk") to point to the "root" directory without any actual redirecting, for example, I want "http://tomblanchard.co.uk" to point to the "index.html" file within the "root" directory, I want "http://tomblanchard.co.uk/blog" to point to the "index.html" file within the "root/blog" directory and so on.
I have kind of achieved this with the following code in my ".htaccess" file:
# Add directives
RewriteEngine on
# Remove ".html" extension from URLs
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}\.html -f
RewriteRule ^(.*)$ $1.html
# Change root directory to "root" folder
Options +FollowSymLinks
RewriteCond %{REQUEST_URI} !(.*)root
RewriteRule ^(.*)$ root/$1 [L]
The only problem is that things like "http://tomblanchard.co.uk/root/" and "http://tomblanchard.co.uk/root/blog/" still work when really they shouldn't even be able to be accessed (404).
If anyone has any idea on how to sort this or has a stronger method of doing this it would be greatly appreciated.
Update
Finally got it working how I wanted it after hours of researching, I used the following:
# Add directives
RewriteEngine on
# Change root directory to "root" folder
RewriteCond %{THE_REQUEST} ^GET\ /root/
RewriteRule ^root/(.*) /$1 [L,R=301]
RewriteRule !^root/ root%{REQUEST_URI} [L]
The order of directives in mod_rewrite is important, as each rule sees the output of the previous rule as its input to test. You need to do 3 (or possibly 4) things, in order:
Deny access to any URL beginning /root/ (we have to do this first, else everything will be denied!)
It's generally good practice to ensure each URL has only one valid form, so URLs which do specify .html should cause a browser redirect to the non-.html form. This needs to happen before other rewrites, otherwise you can't tell the difference between a .html from the browser and one you've added virtually.
Look up any URL not denied above in the /root/ directory, rather than the configured DocumentRoot
Look up any URL not pointing at a directory under the URL + .html, if that file exists. This has to come after other rewrites, or the "file exists" check will always fail.
# General directives
Options +FollowSymLinks
RewriteEngine on
# Deny URLs beginning /root/, faking them as a 404 Not Found
RewriteRule ^root/ [R=404]
# Additional rule to strip .html off URLs in the browser
RewriteRule ^(.*)\.html$ $1 [R=permanent,L]
# Rewrite everything remaining to the /root sub-directory
# (Host condition was in your post originally, then edited out; this is where it would go)
RewriteCond %{HTTP_HOST} ^(www\.)?tomblanchard\.co\.uk$
RewriteRule ^(.*)$ root/$1
# Handle "missing" ".html" extension from URLs
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}\.html -f
RewriteRule ^(.*)$ $1.html
PS: Note my careful language to describe (internal) rewrites, as opposed to (browser) redirects: the rule you have is not removing .html from anything, it is adding it, thus allowing the page to be accessed if someone else removes it. Since you are often modifying both within a set of rules, it's important to keep clear in your head the distinction between the URL the browser has requested, and the virtual URL Apache will ultimately serve.
You are not defining any rule to block /root address so how do you want to block it when there is nothing to do that?
Try this:
# Add directives
RewriteEngine on
RewriteCond %{REQUEST_URI} .root [NC]
RewriteRule (.*) / [L,R=404]
# Remove ".html" extension from URLs
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}\.html -f
RewriteRule ^(.*)$ $1.html
# Change root directory to "root" folder
RewriteCond %{HTTP_HOST} ^tomblanchard.co.uk$ [NC,OR]
RewriteCond %{HTTP_HOST} ^www.tomblanchard.co.uk$
RewriteCond %{REQUEST_URI} !.root
RewriteRule (.*) /root/$1 [L,R=301,QSA]
This is not tested so if it wouldn't work, play around with it to get your need.

.htaccess - When there is no requested URI

I'm looking to do a .htaccess file that let any requests pass to its original destination but redirects to a specific folder (a splash screen in this case) is no destination is specified. I'm not very well-versed with .htaccess and would appreciate some help.
Example: I'm requesting http://www.domain.com/folder/file.php, it should go through. But if I'm requesting http://www.domain.com/, it should redirect to http://www.domain.com/splash/.
What I have so far redirects correctly to /splash/, but redirects everything to /splash/.
<IfModule mod_rewrite.c>
RewriteEngine On
# If the requested URI is empty...
RewriteCond %{REQUEST_URI} !^$
# ...then redirect to the "splash" folder
RewriteRule .* splash [L]
# Otherwise rewrite the base
RewriteBase /
# If the request is not a folder or a file, redirects to index.php
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
</IfModule>
Thanks!
EDIT: One important point would be to redirect http://www.domain.com/ to http://www.domain.com/splash/, but allow direct access to http://www.domain.com/index.php.
The %{REQUEST_URI} variable includes a leading slash, so it will NEVER be blank. You can get rid of that and just use this rule:
RewriteRule ^/?$ /splash/ [L,R]
If you want the URL that appears in the browser's address bar to stay http://www.domain.com/, then remove the ,R from the square brackets: [L].

How to swap "index.php?" with "index.php#" in URL strings via htaccess mod_rewrite

I have a static copy of my original dynamic site. The original site had urls something like this:
http://www.example.com/index.php?module=prodreviews&func=showcontent&id=728
However, since I now have a static copy of my site, all the urls have # instead of ? and an .htm extension.
So current url format: http://www.example.com/index.php#module=prodreviews&func=showcontent&id=728.htm
What are the mod_rewrite rules that will redirect any requests for the old URL structure (the "?" in the url and no .htm extension) to the new URL format? I'd basically like to enable anyone that comes to my site via an old link will be taken to the right page, even though the URL format has changed.
I've been playing around with writing some rules, but no dice.
Here's what I have so far, but this only adds a .htm extension on any URL automatically. I still need to replace any URL requests that have a "?" after the "php" with "#":
Options +FollowSymlinks Options +Indexes RewriteEngine On RewriteBase /
# add .html file extension
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}\.htm -f
RewriteRule ^(.+)$ $1.htm [L]
You need to include the query string as part of your rewrite rule's target:
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}#%{QUERY_STRING}\.htm -f
RewriteCond %{QUERY_STRING} ^(.*)$
RewriteRule ^(.*)$ /$1#%1.htm? [L]

htaccess redirecting issue

My current .htaccess:
<IfModule mod_rewrite.c>
# Turn on URL rewriting
RewriteEngine On
# Put your installation directory here:
# If your URL is www.example.com/, use /
# If your URL is www.example.com/kohana/, use /kohana/
RewriteBase /
# Do not enable rewriting for files or directories that exist
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
# For reuests that are not actual files or directories,
# Rewrite to index.php/URL
RewriteRule ^(.*)$ index.php/$1 [PT,L]
</IfModule>
When someone navigates to:
http://mysite.com/demo/test
I want them to go to the actual folder. When someone navigates to:
http://mysite.com/demo
I want them to go to index.php/$1.
How can I achieve this?
Your rule should work as it is only applied if the requested URL can not be mapped to an existing file (!-f) and not to an existing folder (!-d). So if /demo/test is an actual folder, the second condition (RewriteCond %{REQUEST_FILENAME} !-d) should fail. And if /demo is requested and is neither an existing regular file nor an existing folder it should be redirected to /index.php/demo.

Resources