Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

htaccess - Redirect to subfolder without changing browser URL

I've a domain that contains a subfolder with the web app structure. I added a .htaccess on my root domain to point the public folder on my subfolder web app. It works fine, but when I type www.example.com the browser URL changes to www.example.com/subfolder/public, but I would like that it doesn't change.

This is my .htaccess:

RewriteEngine On
RewriteRule ^.*$ subfolder/public [NC,L]

EDIT

This first .htaccess is used to redirect on subfolder/public, where there is an other .htaccess that makes all the works.

Here the code of the second .htaccess located on www.example.com/subfolder/public/:

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} -s [OR]
RewriteCond %{REQUEST_FILENAME} -l [OR]
RewriteCond %{REQUEST_FILENAME} -d
RewriteRule ^.*$ - [NC,L]
RewriteRule ^.*$ index.php [NC,L]
like image 201
Alessandro Staffolani Avatar asked Jan 05 '17 14:01

Alessandro Staffolani


1 Answers

Sorry, just realised what is happening. It has nothing to do with the second .htaccess file in the subdirectory, as mentioned in comments.

RewriteRule ^.*$ subfolder/public [NC,L]

Since public is a physical directory on the file system, you need to include a trailing slash when internally rewriting to that directory. Otherwise, mod_dir is going to try to "fix" the URL by appending a slash - that is where the external redirect is coming from. (mod_dir implicitly triggers an external redirect from subfolder/public to subfolder/public/.)

So, try the following instead in your root .htaccess file:

RewriteRule .* subfolder/public/ [L]

The important thing is the trailing slash. The anchors (^ and $) on the RewriteRule pattern are not required, since you are matching everything. And the NC flag is also not required for the same reason.

As always, make sure the browser cache is clear before testing.


UPDATE#1: The single directive above rewrites everything, including static resources, to the directory subfolder/public/ which then relies on the second .htaccess file in the subdirectory to correctly route the request. In order to allow static resources to be rewritten correctly (represented in the HTML as root-relative URL-paths, of the form "/js/myjs.js") then you will need additional directives in order to rewrite these.

For example, to specifically rewrite all .js and .css files to the real location in /subfolder/public/...

# Rewrite static resources
RewriteRule (.+\.(?:js|css))$ subfolder/public/$1 [L]

# Rewrite everything else to the "public" directory
RewriteRule .* subfolder/public/ [L]

UPDATE#2: To make the above more general, and to rewrite any static resource (images, PDFs, .txt, etc...) we can check for the existence of the file before rewriting, something like:

# Rewrite static resources
RewriteCond %{DOCUMENT_ROOT}/subfolder/public/$1 -f
RewriteRule (.+) subfolder/public/$1 [L]

# Rewrite everything else to the "public" directory
RewriteRule .* subfolder/public/ [L]

This will mean that if any .css does not exist it will be passed through to subfolder/public/.

like image 197
MrWhite Avatar answered Nov 17 '22 05:11

MrWhite