我的 Tomcat 在端口 8080 上运行,当我直接向 Tomcat 发送请求时,它可以正常工作:
curl -IL http://localhost:8080/myapp
HTTP/1.1 302 Moved Temporarily
Server: Apache-Coyote/1.1
Location: http://localhost:8080/myapp/
HTTP/1.1 302 Moved Temporarily
Server: Apache-Coyote/1.1
Location: http://localhost:8080/myapp/login.html
HTTP/1.1 200 OK
Server: Apache-Coyote/1.1
我在 Apache 中有以下 mod_proxy 设置:
ProxyRequests Off
ProxyPreserveHost on
ProxyPass /myapp http://localhost:8080/myapp retry=0
ProxyPassReverse /myapp http://localhost:8080/myapp retry=0
当我发出通过代理的请求时,Tomcat 会给出 404 错误。标头显示为 Apache-Coyote,因此我知道它正在通过代理到达 Tomcat。
curl -LI https://myserver.com/myapp
HTTP/1.1 404 Not Found
Server: Apache-Coyote/1.1
我启用了 Tomcat 中的访问日志来查看问题所在,Tomcat 的访问日志记录了直接发送到端口 8080 的任何请求,但没有记录通过 Apache 的任何请求。
如果 Apache 破坏了请求或类似情况,我希望在 Tomcat 的日志中看到相关证据。有人能告诉我如何让 Tomcat 记录通过代理的 404 错误,就像记录不通过代理的 404 错误一样吗?
编辑我还注意到,只有当它是配置的一部分时才会发生 404。ProxyPreserveHost on
如果我删除它,代理将完全按预期工作。但我确实需要代理将主机名传递给 Tomcat。
编辑我现在已经设置了 LogLevel Debug,它会在错误日志中显示完整的代理连接。不幸的是,我仍然看不到 404 的来源,但以下是连接:
[Thu Jan 30 11:42:40 2014] [debug] proxy_util.c(1506): [client 10.100.10.38] proxy: http: found worker http://localhost:8080/myapp for http://localhost:8080/myapp
[Thu Jan 30 11:42:40 2014] [debug] mod_proxy.c(1020): Running scheme http handler (attempt 0)
[Thu Jan 30 11:42:40 2014] [debug] mod_proxy_ajp.c(677): proxy: AJP: declining URL http://localhost:8080/myapp
[Thu Jan 30 11:42:40 2014] [debug] mod_proxy_http.c(1973): proxy: HTTP: serving URL http://localhost:8080/myapp
[Thu Jan 30 11:42:40 2014] [debug] proxy_util.c(2011): proxy: HTTP: has acquired connection for (localhost)
[Thu Jan 30 11:42:40 2014] [debug] proxy_util.c(2067): proxy: connecting http://localhost:8080/myapp to localhost:8080
[Thu Jan 30 11:42:40 2014] [debug] proxy_util.c(2193): proxy: connected /myapp to localhost:8080
[Thu Jan 30 11:42:40 2014] [debug] proxy_util.c(2444): proxy: HTTP: fam 2 socket created to connect to localhost
[Thu Jan 30 11:42:40 2014] [debug] proxy_util.c(2576): proxy: HTTP: connection complete to 127.0.0.1:8080 (localhost)
[Thu Jan 30 11:42:40 2014] [debug] mod_proxy_http.c(1851): proxy: header only
[Thu Jan 30 11:42:40 2014] [debug] proxy_util.c(2029): proxy: HTTP: has released connection for (localhost)
答案1
如果您的“代理访问”不是通过 https 复制过去的错误,那么我建议您检查 vhost 配置中的 SSL。
据我所知,您需要在正常的 *:80 和 *:443 Virtualhost 指令中设置 mod_proxy。
因此,您的 Virtualhost 指令没有该条目,或者您应该向我们显示 *:443 条目,以便更具体地帮助您。
答案2
这并不能解释为什么使用 会出现 404 错误ProxyPreserveHost On
,而使用 却不会出现 404 错误ProxyPreserveHost Off
,但是我找到了一种可以让我关闭 ProxyPreserveHost 的解决方法。
我没有让 Apache 将主机名传递给 Tomcat,而是直接将主机名放在 Tomcat 的 server.xml 中,如所述http://tomcat.apache.org/tomcat-6.0-doc/proxy-howto.html。
proxyName="www.mycompany.com"
proxyPort="80"/>
如果有许多不同的主机名通过代理,那么这不是一个有效的解决方法,但我没有。不过,如果有人能想出一种方法让我打开 ProxyPreserveHost,那就太好了。
答案3
但我确实需要代理将主机名传递给 Tomcat。
备选答案。如果后端对原始Host:
标头感兴趣,我认为最好修改后端应用程序以处理X-Forwarded-Host:
标头,并让 apache httpd 准备此类标头(以及其他X-Forwarded-*
标头)。
这样,您就不需要浏览器 URL 和Host:
标头始终指向同一个名称。换句话说,您不再依赖任何名称ProxyPreserveHost on
。您还可以使用多个主机名。