mod_rewriteはApache httpdに標準搭載されたURLリライトモジュールで、HTTPSリダイレクト・旧URL移転・スラッシュ統一といった現場で必要なURL制御をすべて実現できます。ただし「AllowOverride」設定の不備や「RewriteEngine On」の書き忘れが原因で「書いたのに動かない」状態に陥りやすいモジュールでもあります。
この記事では、mod_rewriteの有効化確認から
RewriteRuleとRewriteCondの構文解説、よく使う実践パターン、そして「効かない時のデバッグ手順」まで、RHEL 9 / Ubuntu 24.04 LTSの実機で確認した手順を解説します。この記事のポイント
・LoadModule確認とAllowOverride All設定が前提
・[R=301,L]フラグで301リダイレクトを実現
・RewriteCondでHTTPS強制・www統一などの条件付けが可能
・効かない時はLogLevel rewrite:trace3でデバッグ
でも安心してください。プロのエンジニアはコマンドを暗記していません。
「現場で使える型」を効率よく使いこなしているだけです。
mod_rewriteとは(役割とApache設定上の位置づけ)
mod_rewriteはApache httpdに組み込まれたURLリライトエンジンです。受信したHTTPリクエストのURLパスを正規表現でマッチさせ、別のURLに書き換える(リライト)またはクライアントにリダイレクトする仕組みを提供します。設定は2か所に書けます。
・httpd.conf / VirtualHostブロック内:サーバー全体またはバーチャルホスト単位の設定。変更後にリロードが必要
・.htaccess:ディレクトリ単位の設定。リロード不要だが
AllowOverrideが有効である必要がある現場では「.htaccessに書いて即時反映できる」運用が多いですが、AllowOverrideの設定漏れが「書いたのに動かない」原因のほとんどを占めます。次のセクションで確認手順を説明します。
mod_rewriteを有効化する3ステップ
1. LoadModuleが有効かを確認する
まずmod_rewriteが組み込まれているかを確認します。# RHEL 9 / CentOS 系 $ httpd -M 2>/dev/null | grep rewrite rewrite_module (shared) # Ubuntu 24.04 LTS 系 $ apache2ctl -M 2>/dev/null | grep rewrite rewrite_module (shared)
rewrite_module (shared)が表示されれば有効です。出力がなければ以下で有効化します。# Ubuntu 系(a2enmod を使う) $ sudo a2enmod rewrite $ sudo systemctl restart apache2 # RHEL 系(conf.modules.d の LoadModule 行を確認) # /etc/httpd/conf.modules.d/00-base.conf LoadModule rewrite_module modules/mod_rewrite.so
2. AllowOverrideを設定する
.htaccessが機能するには、対象ディレクトリにAllowOverride All(またはAllowOverride FileInfo)が設定されている必要があります。# /etc/httpd/conf/httpd.conf または VirtualHost ブロック <Directory "/var/www/html"> Options FollowSymLinks AllowOverride All Require all granted </Directory>
AllowOverride None(デフォルトの場合あり)のままだと.htaccessの設定が一切無視されます。設定後はhttpd -tで構文チェックを行い、リロードしてください。$ sudo httpd -t Syntax OK $ sudo systemctl reload httpd
3. .htaccessにRewriteEngineをOnにする
.htaccessを使う場合、ファイルの先頭に必ずRewriteEngine Onを置きます。# /var/www/html/.htaccess RewriteEngine On
RewriteRuleの基本構文
RewriteRuleの基本形は次のとおりです。RewriteRule パターン 置換先 [フラグ]
/は含まない)。フラグは角括弧に入れてカンマ区切りで複数指定できます。主なフラグは以下のとおりです。
・R=301:301(恒久移転)リダイレクト。R=302なら一時移転
・L:このルールで処理を終了する(Last。ループ防止のため重要)
・NC:大文字小文字を区別しない(No Case)
・QSA:元のクエリ文字列を追記する(Query String Append)
例として
/old-pageを/new-pageに301リダイレクトするルールは以下です。RewriteEngine On RewriteRule ^old-page/?$ /new-page [R=301,L]
/?はトレーリングスラッシュの有無に両対応するためのものです。Lフラグを忘れるとルールが連続して実行され、意図しないリダイレクトループが発生します。RewriteCondで条件を追加する
RewriteCondはその直後のRewriteRuleを実行する条件を指定します。条件が偽の場合、RewriteRuleはスキップされます。RewriteCond テスト変数 条件パターン [フラグ] RewriteRule パターン 置換先 [フラグ]
・%{HTTPS}:
onまたはoff(HTTPS接続かどうか)・%{HTTP_HOST}:リクエストのHostヘッダー(例: example.com)
・%{REQUEST_URI}:リクエストのURIパス部分
・%{SERVER_PORT}:接続ポート番号(80または443)
条件パターンの先頭に
!を付けると否定になります。!onは「onでない場合」を意味します。よく使う実践パターン
1. HTTPSへの強制リダイレクト
RewriteEngine On RewriteCond %{HTTPS} !on RewriteRule ^(.*)$ https://%{HTTP_HOST}/$1 [R=301,L]
%{HTTPS} !onでHTTPS以外の接続に限定し、全URLをHTTPS版にリダイレクトします。$1はパターン^(.*)$のキャプチャグループで元のパスを引き継ぎます。ApacheよりもNginxやAWSロードバランサーを前段に置く構成では、実際のHTTPS接続がApacheにはHTTPとして届く場合があります。その場合は
X-Forwarded-Protoヘッダーを条件にします。# ロードバランサー配下の場合 RewriteCond %{HTTP:X-Forwarded-Proto} !https RewriteRule ^(.*)$ https://%{HTTP_HOST}/$1 [R=301,L]
2. wwwあり/wwwなしの統一
# www なし → www ありに統一する場合 RewriteEngine On RewriteCond %{HTTP_HOST} !^www\. [NC] RewriteRule ^(.*)$ https://www.%{HTTP_HOST}/$1 [R=301,L] # www あり → www なしに統一する場合 RewriteEngine On RewriteCond %{HTTP_HOST} ^www\.(.+)$ [NC] RewriteRule ^(.*)$ https://%1/$1 [R=301,L]
%1はRewriteCondの1つ目のキャプチャグループ(ドメイン部分)を参照します。3. 旧URLから新URLへの301移転
# 旧URLの例: /blog/old-article → /articles/new-article RewriteEngine On RewriteRule ^blog/old-article/?$ /articles/new-article [R=301,L]
4. トレーリングスラッシュの統一
# /page → /page/ にスラッシュを追加する(ファイルへのリクエストは除外) RewriteEngine On RewriteCond %{REQUEST_FILENAME} !-f RewriteRule ^(.*[^/])$ /$1/ [R=301,L]
%{REQUEST_FILENAME} !-fでファイルへのリクエスト(.htmlや画像等)を除外します。ファイルにスラッシュを追加すると404になるためです。Linuxサーバー上でApacheをはじめとするWebサーバーを本番環境に適切に設定する方法は、Linux Master Pro Seminarの実機ハンズオンで体系的に習得できます。
mod_rewriteが効かない時のトラブルシュート
1. AllowOverrideの設定を確認する
最初に確認すべきはAllowOverrideの設定です。# httpd.conf で対象ディレクトリの設定を確認 $ grep -A3 'Directory "/var/www/html"' /etc/httpd/conf/httpd.conf <Directory "/var/www/html"> AllowOverride All ← All または FileInfo が必要
AllowOverride Noneになっていると.htaccessが一切読み込まれません。変更後はsystemctl reload httpdを忘れずに実行してください。2. RewriteEngineがOnになっているか確認する
# .htaccess の先頭行を確認 $ head -3 /var/www/html/.htaccess RewriteEngine On ← この行がないと全ルールが無効
3. LogLevelでデバッグログを有効にする
設定が正しいはずなのに動かない場合は、LogLevelを上げてデバッグログを取得します。# httpd.conf または VirtualHost ブロックに追記 LogLevel warn rewrite:trace3 # リロード $ sudo systemctl reload httpd # ログでマッチング状況を確認(RHEL 系) $ sudo tail -f /var/log/httpd/error_log | grep rewrite [Thu Oct 08 14:23:11.504103 2026] [rewrite:trace3] [pid 12345] mod_rewrite.c(475): applying pattern '^old-page/?$' to uri 'blog/old-article'
trace3にするとリクエストごとにルールのマッチング結果が記録されます。原因特定後は必ずwarnに戻してください(ログが大量になります)。Apacheのタイムアウト設定やアクセスログ設定など他の設定との干渉がないかはApache タイムアウト設定の詳細も合わせて確認するとよいでしょう。
4. よくあるミスのチェックリスト
・Lフラグ忘れ:ルールが連続して実行されリダイレクトループが発生する・HTTPSリダイレクトと旧URL移転の2つのR=301が連続している:順序や条件を整理する
・
^(.*)$のパターンが広すぎて静的ファイルも書き換えている:%{REQUEST_FILENAME} !-fで除外する・httpd.conf側のルールと.htaccessのルールが二重になっている:どちらか一方に統一する
本記事のまとめ
| やりたいこと | 設定のポイント |
|---|---|
| mod_rewriteを有効化する | httpd -M | grep rewriteでモジュール確認。AllowOverride Allが必要 |
| HTTPSへの強制リダイレクト | RewriteCond %{HTTPS} !onの後にRewriteRuleを置く |
| 旧URLを新URLへ301移転 | RewriteRule ^旧パス/?$ /新パス [R=301,L] |
| www統一・スラッシュ統一 | RewriteCond %{HTTP_HOST}でホスト名条件を追加する |
| 設定が効かない | AllowOverride確認 → RewriteEngine On確認 → LogLevel rewrite:trace3 |
3,100名以上が実践した「型」を無料で公開中
プロのエンジニアはコマンドを暗記していません。
「現場で使える型」を効率よく使いこなしているだけです。
その「型」を図解60Pにまとめた入門マニュアルを、完全無料でプレゼントしています。
姓・名・メールの3つだけ/30秒/解除は3秒 / 詳細はこちら
- 前のページへ:logresolveコマンドでApacheログのIPアドレスをホスト名に変換する方法
- この記事の属するカテゴリ:Webサーバー管理へ戻る

無料メルマガで学習を続ける
Linuxの実践スキルをメールで毎週お届け。
登録は30秒、解除もいつでも可。
登録無料・いつでも解除できます