いくつかの.htaccess
トリック。 RewriteBase
ディレクティブに遭遇しましたが、正しく機能させることができませんでした。
このディレクティブが具体的に何をし、どのように使用するのか疑問に思います。 StackOverflowおよびApacheドキュメントでRewriteBase
についていくつかの議論がありましたが、それでも、私の質問に対する明確な答えを得ることができませんでした。
誰かがRewriteBase
を使用できるシンプルだが効果的な例を見せてくれませんか?
Htaccessファイルでは、mod_rewriteは<Directory>
または<Location>
コンテナと同様に機能します。 RewriteBase
は、相対パスベースを提供するために使用されます。
たとえば、次のフォルダー構造があるとします。
root
|-- subdir1
|-- subdir2
|-- subsubdir
以下にアクセスできます:
http://example.com/
(ルート)http://example.com/subdir1
(subdir1)http://example.com/subdir2
(subdir2)http://example.com/subdir2/subsubdir
(サブサブディレクトリ)RewriteRule
を介して送信されるURIは、ディレクトリに相対的です。あなたが持っている場合:
RewriteRule ^(.*)$ -
ルートで、リクエストが/a/b/c/d
の場合、キャプチャされたURI($1
)はa/b/c/d
です。ただし、ルールがsubdir2
にあり、リクエストが/subdir2/e/f/g
である場合、キャプチャされたURIはe/f/g
です。ルールがsubsubdir
にあり、リクエストが/subdir2/subsubdir/x/y/z
である場合、キャプチャされたURIはx/y/z
です。ルールが含まれるディレクトリには、その部分がURIから取り除かれています。書き換えベースはこれに影響を与えません。これは単にディレクトリごとの動作です。
書き換えベースが行うことは、URLパスベースを提供します(notファイルパスベース)ルールのターゲット内の相対パス。このルールがあるとしましょう:
RewriteRule ^foo$ bar.php [L]
bar.php
は相対パスです:
RewriteRule ^foo$ /bar.php [L]
ここで、/bar.php
は絶対パスです。絶対パスは、always(上記のディレクトリ構造内の)「ルート」になります。つまり、ルールが「root」、「subdir1」、「subsubdir」などにある場合、/bar.php
パスは常にhttp://example.com/bar.php
にマッピングされます。
ただし、相対パスを使用するもう1つのルールは、ルールが含まれているディレクトリに基づいています。
RewriteRule ^foo$ bar.php [L]
「ルート」にあり、http://example.com/foo
にアクセスすると、http://example.com/bar.php
が提供されます。ただし、そのルールが「subdir1」ディレクトリにあり、http://example.com/subdir1/foo
に移動すると、http://example.com/subdir1/bar.php
が提供されます。等。これは時々機能し、時には機能しません。ドキュメントにあるように、相対パスではrequiredになっているはずですが、ほとんどの場合そうです働く。リダイレクトする場合を除き(R
フラグを使用するか、ルールのターゲットにhttp://Host
があるために暗黙的に)。それはこのルールを意味します:
RewriteRule ^foo$ bar.php [L,R]
「subdir2」ディレクトリにあり、http://example.com/subdir2/foo
に移動すると、mod_rewriteは相対パスをURLパスではなくファイルパスと間違え、R
フラグがあるため、 http://example.com/var/www/localhost/htdocs/subdir1
のようなものにリダイレクトされることになります。これは明らかにあなたが望むものではありません。
これがRewriteBase
の出番です。ディレクティブはmod_rewriteにすべての相対パスの先頭に追加するものを指示します。だから私が持っている場合:
RewriteBase /blah/
RewriteRule ^foo$ bar.php [L]
そのルールは「subsubdir」にあり、http://example.com/subdir2/subsubdir/foo
に移動すると、実際にhttp://example.com/blah/bar.php
が処理されます。 「bar.php」がベースの最後に追加されます。実際には、同じディレクトリコンテナまたはhtaccessファイルに複数のベースを置くことはできないため、この例は通常は望みのものではありません。
ほとんどの場合、次のように使用されます。
RewriteBase /subdir1/
RewriteRule ^foo$ bar.php [L]
これらのルールは「subdir1」ディレクトリにあり、
RewriteBase /subdir2/subsubdir/
RewriteRule ^foo$ bar.php [L]
「subsubdir」ディレクトリにあります。
これにより、ルールを移植可能にすることができるため、ルールを任意のディレクトリにドロップでき、ルールの束ではなくベースを変更するだけで済みます。たとえば、次の場合:
RewriteEngine On
RewriteRule ^foo$ /subdir1/bar.php [L]
RewriteRule ^blah1$ /subdir1/blah.php?id=1 [L]
RewriteRule ^blah2$ /subdir1/blah2.php [L]
...
http://example.com/subdir1/foo
に行くとhttp://example.com/subdir1/bar.php
などになります。これらのファイルとルールをすべて「subsubdir」ディレクトリに移動することにしたとします。 /subdir1/
のすべてのインスタンスを/subdir2/subsubdir/
に変更する代わりに、ベースを作成することもできます。
RewriteEngine On
RewriteBase /subdir1/
RewriteRule ^foo$ bar.php [L]
RewriteRule ^blah1$ blah.php?id=1 [L]
RewriteRule ^blah2$ blah2.php [L]
...
そして、それらのファイルとルールを別のディレクトリに移動する必要があるときは、ベースを変更するだけです:
RewriteBase /subdir2/subsubdir/
以上です。
RewriteBase
は、mod_rewrite
は、RewriteRule
の結果に自動的にプレフィックスを付けます。 .htaccessのコンテキスト内での書き換えは、その.htaccessファイルを含むディレクトリに対して行われます。 RewriteRuleの直接の結果は、まだ.htaccessファイルを含むディレクトリに対して相対的ですが、mod_rewriteはこの結果を調整し、代わりにドキュメントルートに対して相対的にします。 RewriteBase
を使用すると、この最後の手順を変更して、RewriteRuleの結果の直前に追加される任意のbaseパスを提供できます。 、ドキュメントルートの代わりに。
私にとって、RewriteBase
ディレクティブを理解するキーポイントは、mod_rewriteがRewriteBase
を結果に適用することに気づいたときです引数ではなく、RewriteRules
の。
.htaccessファイルのコンテキスト内でのRewriteRule
の通常の処理は次のようになります。
/doc_root/one/.htaccess
、生成されるパスは/two/three
。このプロセスにより、ドキュメントルートに対する相対パスが書き換えられます。
RewriteBase
ディレクティブがある場合、ステップ1、2、および3は同じままで、ステップ4のみが変更されます。ドキュメントルートの代わりに、.htaccessファイルを含むディレクトリへのファイルシステムパスが削除されます。次に、RewriteBase
が付加されます。
例:
https://example.com/one/two/three/file.txt
/var/doc_root
/var/doc_root/one/.htaccess
/var/other_location/
HtaccessファイルにRewriteBaseがない場合、これは次のように処理されます。
/two/three/file.txt
/four/rewritten.txt
/var/do_root/one/four/rewritten.txt
one/four/rewritten.txt
.htaccessファイルのRewriteBaseを使用すると、これは次のように処理されます。
/two/three/file.txt
/four/rewritten.txt
/var/other_location/four/rewritten.txt