http://www.siven.net/posts/d925bb5d.htmlhtml
***********************************************nginx
因为要配置服务器(Nginx + Tomcat)的SSL的问题(Nginx同时监听HTTP
和HTTPS
),可是,若是用户访问的是HTTPS
协议,而后Tomcat进行重定向的时候,却变成了HTTP
.apache
在网上找了一些资料,有些是经过修改Nginx配置便可解决,也有只对Tomcat配置进行调整解决的… 各说不一,如下对尝试的解决过程进行记录:tomcat
HTTP协议制转为https服务器
Nginx代理的配置,要添加如下内容:session
location / {
proxy_pass http://test-server;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# 必须配置:
proxy_set_header X-Forwarded-Proto $scheme;
# 做用是对发送给客户端的URL进行修改, 将http协议强制转为https
proxy_redirect http:// https://;
}
为了方便测试强制转换, http(80)、https(443)共存proxy_redirect
server {
listen 80;
listen 443 ssl;
...
}
JAVA CODE:app
HttpServletResponse resp = (HttpServletResponse)response;
resp.sendRedirect("/static/html/index.html");
使用HTTP
协议访问nginx
代理地址以后,URL被重定向为HTTPS
协议了, 以下图所示:dom
固然直接使用HTTPS协议访问, 确定也是没有问题的,以下图所示:post
JAVA CODE:测试
HttpServletResponse resp = (HttpServletResponse)response;
req.getRequestDispatcher("/static/html/index.html").forward(request, response);
测试结果与重定向一致, 无异常状况;
实际应用场景中,若是要求HTTP
与HTTPS
协议共存的时候(请求的协议与响应的协议一致)就会出现HTTP
请求被强转为HTTPS
,尝试将Nginx配置proxy_redirect http:// https://;
注释,最终使用HTTPS
协议亦没法正常跳转;
不修改Nginx的状况下, 仅对Tomcat配置进行调整
在server.xml
的Engine
模块下面配置多一个如下的Valve
<Valve className="org.apache.catalina.valves.RemoteIpValve" remoteIpHeader="X-Forwarded-For" protocolHeader="X-Forwarded-Proto" protocolHeaderHttpsValue="https"/>
使用HTTPS
协议访问时,最终被重定向到HTTP
使用HTTPS
协议访问,转发动做未出现问题
重定向的时候, HTTPS
协议被转为HTTP
,测试结果不经过。
对过程一Nginx配置进行调整注释或删除proxy_redirect
,最终以下:
location / {
proxy_pass http://test-server;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# 必须配置:
proxy_set_header X-Forwarded-Proto $scheme;
}
参看:Tomcat配置
测试经过,不管使用HTTP访问仍是HTTPS访问,最终返回都是根据请求的协议进行响应,问题解决。
worker_processes 1;
events {
worker_connections 1024;
}
http {
include mime.types;
default_type application/octet-stream;
sendfile on;
keepalive_timeout 65;
upstream test-server {
server 10.15.16.6:8280 weight=1;
}
server {
listen 80;
listen 443 ssl;
server_name localhost;
#ssl_certificate cert.pem;
#ssl_certificate_key cert.key;
ssl_certificate server.crt;
ssl_certificate_key server.key;
# ssl_session_cache shared:SSL:1m;
#ssl_session_timeout 5m;
# ssl_ciphers HIGH:!aNULL:!MD5;
# ssl_prefer_server_ciphers on;
location / {
proxy_pass http://test-server;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
# proxy_redirect http:// https://;
}
}
}
//处理代码段
domainName = request.getRequestURL().toString(); String X_Forwarded_Proto = httpRequest.getHeader("X-Forwarded-Proto"); if(StringUtils.isNotBlank(X_Forwarded_Proto)){ if(X_Forwarded_Proto.toLowerCase().contains("https") && !domainName.toLowerCase().startsWith("https://")){ domainName = "https://" + domainName.substring(7); } }