.htaccess によるリダイレクト
PHPモジュール化やページ分割のカスタマイズを行った場合、ファイルの拡張子が .html から .php に変更になります。拡張子を変更すると、他サイトからそのファイルにリンクを貼っている場合、デッドリンク(404 Not Found)になってしまいます。
ここでは .htaccess を用いたリダイレクト(転送)によりデッドリンクを回避する方法を紹介します。
動作を簡単に説明すると、.htaccess という特殊なファイルに
hogehoge.html へのアクセスを hogehoge.php に転送する
という内容を設定し、一定の場所に配置しておくだけで hogehoge.html へのアクセスが自動的に hogehoge.php に転送されます。hogehoge.html の実体がなくても大丈夫です。
1..htaccess のフォーマット
.htaccess でリダイレクトをするための正式なフォーマットは、
RedirectPermanent URL-path URL
となります。URL-path が元URL、URLが転送先URLです。例えば archives/hogehoge.html を 同じディレクトリの hogehoge.php に転送する場合は
RedirectPermanent /blog/archives/hogehoge.html http://user-domain/blog/archives/hogehoge.php
という内容になります。ドメインを移行する場合も同様です。
フォーマットの URL-path は、ドキュメントルートからのパス(root からの絶対パスではありません)を指定し、先頭に "/" を付与してください。「ドキュメントルート」とはWebサーバがHTMLファイルを公開するためのディレクトリを意味します。
もう少し具体的に説明します。上記の例ではドメインが
http://user-domain/
で、そのドキュメントルートが
/path/to/htdocs
と仮定します。
ドメイン(つまりドキュメントルート)の配下に blog というディレクトリを作り、そこにブログの index.html が配置されている場合、index.html までの絶対パスは
/path/to/htdocs/blog/index.html
となります。この場合 .htaccess に記述すべき URL-path は、
/blog/?
と、/blog で開始させます。これが前述の「ドキュメントルートからのパス」という意味です。
ドキュメントルート直下、つまり /path/to/htdocs 直下に index.html を配置している場合は .htaccess に /blog を記述する必要はありません(ただし archives ディレクトリ等がある場合はそれを記述します)。
2..htaccess のアップロード先
.htaccess をアップロードするディレクトリは、ドキュメントルートでも、サイト・パス(ブログの index.html があるディレクトリ)でも大丈夫です。
3..htaccess 生成
.htaccess のリダイレクトの設定は、1ファイルに対して1行ずつ書かなければなりません。例えば、エントリーアーカイブ100ファイルを転送する場合、転送の設定を100行書く必要があります。
この手間を省くためにインデックステンプレートを用いて .htaccess ファイルを一気に生成します。
以下、.htaccess の作成手順です。
3.1 .htaccess 用テンプレート作成
管理メニューの「テンプレート」→「インデックス」で「テンプレートを新規作成」をクリックし、次ページで下記を設定します。
- テンプレート名:リダイレクト(何でもいいです)
- ファイル:htaccess.txt
- テンプレートの内容:下記
<MTArchiveList archive_type="Individual">
RedirectPermanent /blog/archives/<$MTArchiveDate format="%Y/%m"$>/<MTEntries><$MTEntryLink$></MTEntries> <$MTBlogURL$>archives/<$MTArchiveDate format="%Y/%m/%d_%H%M"$><MTEntries>.php</MTEntries>
</MTArchiveList>
<MTArchiveList archive_type="Category">
RedirectPermanent <$MTArchiveLink$>index.html <$MTBlogURL$>archives/cat<$MTCategoryID$>/index.php
</MTArchiveList>
<MTArchiveList archive_type="Monthly">
RedirectPermanent <$MTArchiveLink$>index.html <$MTBlogURL$>archives/<$MTArchiveDate format="%Y/%m"$>/index.php
</MTArchiveList>
リストは上から順に、エントリーアーカイブ/カテゴリー・アーカイブ/月別アーカイブを転送する設定になっています。転送が必要なアーカイブのみを設定してください。
3.2 注意事項
このリストは旧URLのファイル名をデフォルトの状態で生成していることを前提に作っており、この場合2つの注意事項があります。
まずこのファイルの生成は、管理メニューの「設定」→「公開」→「アーカイブ・マッピング」の「出力ファイル名」で新ファイル名を設定する前に行う必要があります。理由は旧ファイル名の生成に MTEntryLink を使用しているためです(MTEntryPermaLink を使っても構いません)。
もしすでに変更してしまっていたら「出力フォーマット」を一旦元の状態に戻して、このインデックステンプレートだけを生成するという手もあります(その際、他のアーカイブテンプレートを再構築しないように注意しましょう)。
もうひとつは、MTタグを使って URL-path を自動的に生成していますが、残念ながらMTタグのみで「ドキュメントルートからのパス+ファイル名」というフォーマットを生成することはできません(いわゆるURL形式で生成されます)。したがって、エントリーアーカイブについては MTEntryLink、カテゴリー・アーカイブ/月別アーカイブについては MTArchiveLink を使い、ファイルを生成した後、任意のエディタで開き、リダイレクトの設定で不要なドメイン部分を削除します。
上記とは別に、すでに「出力フォーマット」欄でファイル名を変更している場合は、URL-path の部分を適宜変更してください。また新URLについてもご自身の設定内容にあわせて適宜修正してください。
3.3 その他
この作業は一度でうまくいかないと思いますので、実際の新旧ファイル名と見比べながら、ファイルに設定したタグを修正することをお勧めします。またこの作業を行う前に、試しに各アーカイブについて1ファイルずつ手書きで .htaccess のリダイレクト設定を行ってみて、旧URLを開いた時に新URLへ転送されることを確認するのも良いでしょう。
4..htaccess アップロード
ファイルの内容がきちんとできたら保存・再構築し、出来上がったファイルを任意のエディタ(メモ帳)等で開き、ファイル名を .htaccess に変更して保存します。すでに .htaccess がある場合は、そのファイルに先の内容を追加します。
テンプレートの出力ファイル名をいきなり .htaccess として保存することも可能ですが、生成された瞬間に設定が有効となるので、一旦別のファイル名で作ることをお勧めします。
5.動作確認
できあがったファイルを .htaccess にリネームして、サイト・パス(index.html があるディレクトリ)にアップロードします。これで旧エントリーアーカイブ(.html)等にアクセスしてみてください。.php のファイルにアクセスできれば成功です。
6.Redirect と RedirectPermanent の違いについて
他のサイトを検索すると、Redirect ディレクティブと RedirectPermanent ディレクティブを使っている例がみられました。Apache2.0 のドキュメントを見てみると、たしかに
- RedirectPermanent 元URL 転送先URL
- Redirect permanent 元URL 転送先URL
の2つの設定方法がありますが、いずれも 301(永久に移動)のHTTPステータスコードを返すので、私の誤解がなければ振る舞いは全く同じです。ただし Redirect ディレクティブに permanent を付与しない場合は 302(一時的な移動)というHTTPステータスコードになりますのでご注意ください。
参考サイトは下記です。ありがとうございました。
- ARTIFACT:MovableTypeのページ分割/Permalinkの変更
- 我楽:PHP化とページ分割。
- Pega Weblog:MTのPHP化?.htaccess編
- Apache HTTP サーバ バージョン 2.0 ドキュメント:Redirect ディレクティブ
- Apache HTTP サーバ バージョン 2.0 ドキュメント:RedirectPermanent ディレクティブ

