これは非常にトリッキーですが、これは、指定されたREQUEST_URIの親ディレクトリに再帰的にトラバースするコードであり、無限の深さをサポートします。
mod_rewriteと.htaccessを有効にしてからhttpd.conf
、次のコードを.htaccess
アンダーDOCUMENT_ROOT
ディレクトリに配置します。
# Turn mod_rewrite on
RewriteEngine On
RewriteBase /
# If the request is for a valid file
RewriteCond %{REQUEST_FILENAME} -f [OR]
# If the request is for a valid link
RewriteCond %{REQUEST_FILENAME} -l
# don't do anything
RewriteRule ^ - [L]
# if current ${REQUEST_URI}.php is not a file then
# forward to the parent directory of current REQUEST_URI
RewriteCond %{DOCUMENT_ROOT}/$1/$2.php !-f
RewriteRule ^(.*?)/([^/]+)/?$ $1/ [L]
# if current ${REQUEST_URI}.php is a valid file then
# load it be removing optional trailing slash
RewriteCond %{DOCUMENT_ROOT}/$1.php -f
RewriteRule ^(.*?)/?$ $1.php [L]
説明:
元のURIが次のようになっているとしましょう/index/foo/bar/baz
。%{DOCUMENT_ROOT}/index.php
また、それは存在しますが、他のphpファイルは。の下に存在しないとしましょうDOCUMENT_ROOT
。
RewriteRule#1には、現在のREQUEST_URIを2つの部分に分割する正規表現があります。
- ここに
$1
ある最低のサブディレクトリを除くすべてindex/foo/bar
- ここに
$2
ある最低のサブディレクトリbaz
%{DOCUMENT_ROOT}/$1/$2.php
RewriteCondは、 (これ%{DOCUMENT_ROOT}/index/foo/bar/baz.php
は)が有効なファイルではないかどうかをチェックします。
条件が成功すると、内部的にここにリダイレクトされ$1/
ますindex/foo/bar/
。
RewriteRule#1のロジックが再度繰り返され、REQUEST_URIが(各再帰の後に)次のようになります。
index/foo/bar/
index/foo/
index/
この時点で、ルール#1が${DOCUMENT_ROOT}/index.php
存在するため、RewriteCondは失敗します。
私のRewriteRule#2は、が有効なファイルである$1.php
かどうかを転送します。%{DOCUMENT_ROOT}/$1.php
RewriteRule#2には、最後のスラッシュ以外のすべてに一致する正規表現があり、それをに入れることに注意してください$1
。これ%{DOCUMENT_ROOT}/index.php
は、が有効なファイルであるかどうかを確認することを意味します(実際に有効です)。
この時点でmod_rewrite処理が完了します。これは、その後両方のRewriteCondが失敗し%{DOCUMENT_ROOT}/index.php
、Apache Webサーバーによって適切に処理されるため、これ以上ルールを実行できないためです。