.htaccess rewrite to subfolder .htaccess rewrite to subfolder apache apache

.htaccess rewrite to subfolder


The reason why this is happening is because of mod_dir. It has a directive called DirectorySlash that redirects the browser when it thinks a request is made for a directory and the trailing slash is missing to the same URI with a trailing slash appended. The problem is mod_dir and mod_rewrite get applied at different places in the URL/file mapping pipeline. So mod_rewrite mangles the URI at one point, then when mod_dir does its thing, the rewritten URI gets redirected so the URL in the browser's address bar changes to include the "hidden" internal rewrite.

You can do a couple of things here.

  1. You can enforce trailing slashes yourself in mod_rewrite, so the browser gets redirected to include the trailing slash before the URI reaches mod_dir. This means all of your URLs for things like /home and /contact will include a trailing slash, if one is missing, your rewrite code will redirect and add one. Something like this, above your current rule so that it gets applied first:

    RewriteCond %{REQUEST_URI} !^/subfolderRewriteCond %{DOCUMENT_ROOT}/subfolder%{REQUEST_URI} !-fRewriteRule ^(.*[^/])$ /$1/ [L,R=301]
  2. Turn off DirectorySlash so mod_dir stops doing this redirect. You can simply include DirectorySlash Off at the top of your htaccess file. However, the downside here is a possible information disclosure security issue when the trailing slash is missing.


EDIT:

In order to use the index file, without a trailing slash, you need to map to it. Try changing your rules to:

    RewriteEngine On    RewriteCond %{REQUEST_URI} !^/subfolder    RewriteCond %{DOCUMENT_ROOT}/subfolder%{REQUEST_URI} -d    RewriteRule ^(.*?)/?$ /subfolder/$1/ [L]    RewriteCond %{REQUEST_URI} !^/subfolder    RewriteRule ^(.*)$ /subfolder/$1 [L]