Apache仅特定域名未实现HTTP到HTTPS重定向的问题排查
问题背景
我有一台运行Apache作为Web服务器的VPS,负责处理某域名及其子域名的请求。为每个域名/子域名配置了如下HTTP到HTTPS的重定向规则:
<IfModule mod_ssl.c> <VirtualHost *:80> ServerName sub.domain.com RewriteEngine on RewriteCond %{SERVER_NAME} =sub.domain.com RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent] </VirtualHost> <VirtualHost *:443> ServerAdmin webmaster@localhost ServerName sub.domain.com DocumentRoot /var/www/html/sub.domain.com [...] </IfModule>
该配置对所有域名均生效,但专用于SMTP的smtp.domain.com例外:其HTTP请求会回退到默认配置(返回/var/www/html/下的index.html),仅显式HTTPS请求可正常工作。执行apache2ctl configtest命令显示配置无问题,怀疑存在配置覆盖。
10月23日排查进展
在apache2.conf中添加LogLevel alert rewrite:trace6开启rewrite模块日志后,对比不同域名的HTTP请求日志发现:
smtp.domain.com未触发重写规则,access.log仅记录:
[23/Oct/2022:11:46:29 +0000] "GET / HTTP/1.1" 403 440 "-" "curl/7.68.0"
imap.domain.com的error.log显示重写规则正常触发:
[Sun Oct 23 11:39:09.846013 2022] [rewrite:trace3] [pid 2390:tid 140516244342528] mod_rewrite.c(483): [client MY_IP_ADDR] MY_IP_ADDR - - [imap.domain.com/sid#7fcc7e661df0][rid#7fcc7c4ec0a0/initial] applying pattern '^' to uri '/' [Sun Oct 23 11:39:09.846144 2022] [rewrite:trace4] [pid 2390:tid 140516244342528] mod_rewrite.c(483): [client MY_IP_ADDR] MY_IP_ADDR - - [imap.domain.com/sid#7fcc7e661df0][rid#7fcc7c4ec0a0/initial] RewriteCond: input='imap.domain.com' pattern='=imap.domain.com' => matched [Sun Oct 23 11:39:09.846166 2022] [rewrite:trace2] [pid 2390:tid 140516244342528] mod_rewrite.c(483): [client MY_IP_ADDR] MY_IP_ADDR - - [imap.domain.com/sid#7fcc7e661df0][rid#7fcc7c4ec0a0/initial] rewrite '/' -> 'https://imap.domain.com/' [Sun Oct 23 11:39:09.846182 2022] [rewrite:trace2] [pid 2390:tid 140516244342528] mod_rewrite.c(483): [client MY_IP_ADDR] MY_IP_ADDR - - [imap.domain.com/sid#7fcc7e661df0][rid#7fcc7c4ec0a0/initial] explicitly forcing redirect with https://imap.domain.com/ [Sun Oct 23 11:39:09.846200 2022] [rewrite:trace1] [pid 2390:tid 140516244342528] mod_rewrite.c(483): [client MY_IP_ADDR] MY_IP_ADDR - - [imap.domain.com/sid#7fcc7e661df0][rid#7fcc7c4ec0a0/initial] redirect to https://imap.domain.com/ [REDIRECT/301]
git diff显示smtp.domain.com与imap.domain.com的配置仅域名不同:
diff --git a/smtp.domain.com.conf b/imap.domain.com.conf index f7778ee..cba26cb 100644 --- a/smtp.domain.com.conf +++ b/imap.domain.com.conf @@ -1,27 +1,20 @@ <IfModule mod_ssl.c> <VirtualHost *:80> - ServerName smtp.domain.com + ServerName imap.domain.com RewriteEngine on - RewriteCond %{SERVER_NAME} =smtp.domain.com + RewriteCond %{SERVER_NAME} =imap.domain.com RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent] </VirtualHost> <VirtualHost *:443> ServerAdmin webmaster@localhost - ServerName smtp.domain.com - DocumentRoot /var/www/html/smtp.domain.com/ + ServerName imap.domain.com + DocumentRoot /var/www/html/imap.domain.com/ # Available loglevels: trace8, ..., trace1, debug, info, notice, warn, # error, crit, alert, emerg.
主配置文件中未提及smtp.domain.com,不存在覆盖规则。
10月23日进一步发现
http://smtp.domain.com的请求被Apache分配到默认配置文件000-default.conf而非自定义的smtp.domain.com.conf,将重写规则添加到默认配置后重定向生效。核心疑问:为何HTTP请求未使用自定义配置?
可能的原因及解决办法
1. 配置文件未被Apache加载
- 检查
smtp.domain.com.conf是否在Apache的配置加载目录(通常为/etc/apache2/sites-available/)中。 - 确认已执行
a2ensite smtp.domain.com.conf启用该站点配置,随后重启Apache生效。 - 查看Apache启动日志(通常在
/var/log/apache2/error.log),确认是否有加载该配置文件的记录。
2. 配置文件命名顺序冲突
Apache按文件名字母顺序加载站点配置,若其他VirtualHost *:80配置在smtp.domain.com.conf之前加载,且包含匹配smtp.domain.com的规则(如ServerAlias *.domain.com通配符),会导致请求被优先匹配到其他配置。
- 检查其他
VirtualHost *:80配置是否存在通配符规则。 - 可修改
smtp.domain.com.conf文件名前缀,例如改为001-smtp.domain.com.conf,使其优先于默认配置000-default.conf加载。
3. <IfModule mod_ssl.c>限制导致HTTP配置未生效
smtp.domain.com的VirtualHost *:80配置被包裹在<IfModule mod_ssl.c>块中,但HTTP 80端口配置无需依赖mod_ssl模块。若mod_ssl加载异常(虽HTTPS正常工作说明已加载,但需确认),该80端口配置会被忽略。
- 将
VirtualHost *:80部分从<IfModule mod_ssl.c>块中移出,单独配置:
<VirtualHost *:80> ServerName smtp.domain.com RewriteEngine on RewriteCond %{SERVER_NAME} =smtp.domain.com RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent] </VirtualHost> <IfModule mod_ssl.c> <VirtualHost *:443> # 原HTTPS配置内容 </VirtualHost> </IfModule>
4. DNS解析或请求头异常
- 确认客户端访问
smtp.domain.com时解析的IP指向目标VPS,无本地Hosts或DNS缓存干扰。 - 用
curl -v http://smtp.domain.com查看请求头中的Host字段是否准确为smtp.domain.com,若Host字段异常,Apache无法匹配对应VirtualHost。
内容的提问来源于stack exchange,提问作者rudicangiotti

