我在其中一台虚拟主机上不断收到太多重定向,但在另一台虚拟主机上则没有。我确信我犯了一些我只是不认识的非常小的错误。我在下面附上了两个 Apache2 站点配置。我已经尝试了几个不同版本的重写条件,但没有任何改变。我每次都重新启动apache。对我来说最有意义的重写规则是这些,由于 OR 优先级,根据我的计算,这些规则应该是
(www.stage OR stage) AND HTTPS=OFF
。看来 HTTPS
检查从未发生过?我完全困惑为什么工作配置的直接副本不适用于这个新站点。
RewriteCond %{SERVER_NAME} =www.stage.example.com [OR]
RewriteCond %{SERVER_NAME} =stage.example.com
RewriteCond %{HTTPS} off
RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
我有几个站点在带有 Apache2 的服务器上的 microk8s pod 中运行,并且虚拟主机将流量传递到适当的端口。这两个网站之间的主要区别在于,一个是用 PHP 编写的(可以运行),而新的一个是用 DJango 编写的。但我有另一个网站是 Django 中的工作网站,所以我怀疑这就是问题所在。
# example.com.config
# Staging branch, unstable wip
# Config also includes 2 other virtual hosts for dev and main as well
<VirtualHost *:80>
ServerName stage.example.com
ServerAlias www.stage.example.com
# Rewrite logs show up in these log files, so I know it's happening in
# this virtual host.
ErrorLog ${APACHE_LOG_DIR}/ex-stage-error.log
CustomLog ${APACHE_LOG_DIR}/ex-stage-access.log combined
ProxyPass / http://localhost:30102/
ProxyPassReverse / http://localhost:30102/
<IfModule mod_rewrite.c>
RewriteEngine on
RewriteCond %{SERVER_NAME} =www.stage.example.com
RewriteCond %{HTTPS} off
RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
RewriteCond %{SERVER_NAME} =stage.example.com
RewriteCond %{HTTPS} off
RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
</IfModule>
</VirtualHost>
<VirtualHost *:443>
ServerName stage.example.com
ServerAlias www.stage.example.com
RequestHeader set X-Forwarded-Proto https
ProxyPreserveHost On
ErrorLog ${APACHE_LOG_DIR}/ex-stage-error.log
CustomLog ${APACHE_LOG_DIR}/ex-stage-access.log combined
ProxyPass / http://localhost:30102/
ProxyPassReverse / http://localhost:30102/
Include /etc/letsencrypt/options-ssl-apache.conf
SSLCertificateFile /etc/letsencrypt/live/example.com/fullchain.pem
SSLCertificateKeyFile /etc/letsencrypt/live/example.com/privkey.pem
</VirtualHost>
# example2.com.conf
# All three of the virtual hosts in this file work as expected.
# I tried copying over the rewrite conditions directly, and nothing changed.
# Main branch, stable production release
<VirtualHost *:80>
ServerName example2.com
ServerAlias www.example2.com
ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined
ProxyPass / http://localhost:30090/
ProxyPassReverse / http://localhost:30090/
RewriteEngine on
RewriteCond %{SERVER_NAME} =example2.com [OR]
RewriteCond %{SERVER_NAME} =www.example2.com
RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>
<VirtualHost *:443>
ServerName example2.com
ServerAlias www.example2.com
RequestHeader set X-Forwarded-Proto https
ProxyPreserveHost On
ErrorLog ${APACHE_LOG_DIR}/error.log
CustomLog ${APACHE_LOG_DIR}/access.log combined
ProxyPass / http://localhost:30090/
ProxyPassReverse / http://localhost:30090/
Include /etc/letsencrypt/options-ssl-apache.conf
SSLCertificateFile /etc/letsencrypt/live/example.com/fullchain.pem
SSLCertificateKeyFile /etc/letsencrypt/live/example.com/privkey.pem
</VirtualHost>
这是错误日志,它似乎是一个重复的块,我在任何地方都没有看到从 https 重写到 http。
[Thu Mar 21 19:54:42.104070 2024] [rewrite:trace2] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] init rewrite engine with requested uri /
[Thu Mar 21 19:54:42.104115 2024] [rewrite:trace3] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] applying pattern '^' to uri '/'
[Thu Mar 21 19:54:42.104131 2024] [rewrite:trace4] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] RewriteCond: input='stage.example.com' pattern='=www.stage.example.com' => not-matched
[Thu Mar 21 19:54:42.104139 2024] [rewrite:trace3] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] applying pattern '^' to uri '/'
[Thu Mar 21 19:54:42.104147 2024] [rewrite:trace4] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] RewriteCond: input='stage.example.com' pattern='=stage.example.com' => matched
[Thu Mar 21 19:54:42.104157 2024] [rewrite:trace4] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] RewriteCond: input='off' pattern='off' => matched
[Thu Mar 21 19:54:42.104183 2024] [rewrite:trace2] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] rewrite '/' -> 'https://stage.example.com/'
[Thu Mar 21 19:54:42.104192 2024] [rewrite:trace2] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] explicitly forcing redirect with https://stage.example.com/
[Thu Mar 21 19:54:42.104201 2024] [rewrite:trace1] [pid 457040:tid 140525785032256] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc36c0a0/initial] redirect to https://stage.example.com/ [REDIRECT/301]
# newline added here
[Thu Mar 21 19:54:42.146666 2024] [rewrite:trace2] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] init rewrite engine with requested uri /
[Thu Mar 21 19:54:42.146695 2024] [rewrite:trace3] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] applying pattern '^' to uri '/'
[Thu Mar 21 19:54:42.146707 2024] [rewrite:trace4] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] RewriteCond: input='stage.example.com' pattern='=www.stage.example.com' => not-matched
[Thu Mar 21 19:54:42.146714 2024] [rewrite:trace3] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] applying pattern '^' to uri '/'
[Thu Mar 21 19:54:42.146723 2024] [rewrite:trace4] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] RewriteCond: input='stage.example.com' pattern='=stage.example.com' => matched
[Thu Mar 21 19:54:42.146731 2024] [rewrite:trace4] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] RewriteCond: input='off' pattern='off' => matched
[Thu Mar 21 19:54:42.146739 2024] [rewrite:trace2] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] rewrite '/' -> 'https://stage.example.com/'
[Thu Mar 21 19:54:42.146746 2024] [rewrite:trace2] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] explicitly forcing redirect with https://stage.example.com/
[Thu Mar 21 19:54:42.146755 2024] [rewrite:trace1] [pid 457040:tid 140525776639552] mod_rewrite.c(480): [client 172.68.27.206:30746] 172.68.27.206 - - [stage.example.com/sid#7fceced53528][rid#7fcecc3680a0/initial] redirect to https://stage.example.com/ [REDIRECT/301]
重写条件由 certbot 在通过 snap 安装的 ubuntu 服务器上插入。我把80虚拟主机改成如下:
<VirtualHost *:80>
ServerName stage.example.com
ServerAlias www.stage.example.com
ErrorLog ${APACHE_LOG_DIR}/ex-stage-error.log
CustomLog ${APACHE_LOG_DIR}/ex-stage-access.log combined
Redirect permanent / https://stage.example.com/
</VirtualHost>
现在错误日志中没有重定向,只有访问重定向:
172.71.166.203 - - [21/Mar/2024:20:38:10 +0000] "GET / HTTP/1.1" 301 622 "-" "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/122.0.0.0 Safari/537.36 OPR/108.0.0.0"
172.71.166.203 - - [21/Mar/2024:20:38:10 +0000] "GET / HTTP/1.1" 301 621 "-" "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/122.0.0.0 Safari/537.36 OPR/108.0.0.0"
172.71.166.203 - - [21/Mar/2024:20:38:10 +0000] "GET / HTTP/1.1" 301 621 "-" "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/122.0.0.0 Safari/537.36 OPR/108.0.0.0"
... 20 times
没有流量到达 Django pod,但我可以
curl localhost:30102
并从应用程序获取预期的页面。
因此,此配置似乎将所有流量发送到 80 而不是 443。我通过curl 发送了一个 https 请求,并从端口 80 获得了重定向。
curl https://stage.example.com
<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN">
<html><head>
<title>301 Moved Permanently</title>
</head><body>
<h1>Moved Permanently</h1>
<p>The document has moved <a href="https://stage.example.com/">here</a>.</p>
<hr>
<address>Apache/2.4.52 (Ubuntu) Server at stage.example.com Port 80</address>
</body></html>
更新后的配置文件如下所示:
<VirtualHost *:80>
ServerName stage.example.com
ServerAlias www.stage.example.com
ErrorLog ${APACHE_LOG_DIR}/taf-stage-error.log
CustomLog ${APACHE_LOG_DIR}/taf-stage-access.log combined
Redirect permanent / https://stage.example.com/
</VirtualHost>
<VirtualHost *:443>
ServerName stage.example.com
ServerAlias www.stage.example.com
RequestHeader set X-Forwarded-Proto https
ProxyPreserveHost On
ErrorLog ${APACHE_LOG_DIR}/taf-stage-error.log
CustomLog ${APACHE_LOG_DIR}/taf-stage-access.log combined
ProxyPass / http://localhost:30102/
ProxyPassReverse / http://localhost:30102/
</VirtualHost>
根据他们的文档,问题在于启用 Cloudflare HTTP 到 HTTPS,并在我的 apache 配置中将 HTTP 重定向到 HTTPS。