阿里云slb配置https重定向后变为http
阿里云slb配置https重定向后变http问题解决
- 背景描述
- 问题
- 部署结构
- 网上搜索到的方案
- 方案一
- 方案二
- 原理剖析
- Servlet容器重定向
- Shiro 重定向
- Spring MVC 重定向
- 总结
- 最佳实践
背景描述
问题
阿里云slb配置443端口监听,然后将80端口的监听配置为重定向到https:443端口。
通过http://abc.com来访问站点,成功跳转至https://abc.com,实现了http强制跳https。
输入账号、密码登录系统,然后 “500”错误,F12浏览器debug发现提示以下错误:
Mixed Content: The page at 'https://abc.com' was loaded over HTTPS, but requested an insecure XMLHttpRequest endpoint 'http://abc.com/onLoginSuccess.html'. This request has been blocked; the content must be served over HTTPS.
部署结构
网上搜索到的方案
方案一
Spring MVC 里面使用到了redirect:/path
,可以通过以下配置来搞定:
<bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver"><!-- redirectHttp10Compatible:解决https环境下使用redirect重定向地址变为http的协议,无法访问服务的问题,设置为false,即关闭了对http1.0协议的兼容支持--> <property name="redirectHttp10Compatible" value="false" /> </bean>
大概意思就是因为代码了做了对http1.0
兼容,导致了重定向以后返回去的就是http了。
方案二
使用了shiro
框架,里面有什么loginUrl
、sucessUrl
之类的配置,这里也会利用redirect进行跳转,具体方案如下:
- 重写RedirectView类,将
http10Compatible
开关关闭; - 硬编码强制修改response Header里面的Location的值;
太复杂了,学不会呀!!!
原理剖析
Servlet容器重定向
Servlet容器Tomcat(tomcat-embed-8.5.31)里面的一个类:org.apache.catalina.connector.Response
里面有这么一段代码:
/*** 如果有需要的话把一个相对地址转化为绝对地址(我自己乱翻译的)*/
protected String toAbsolute(String location) {...boolean leadingSlash = location.startsWith("/");if (location.startsWith("//")) {// Add the schemeString scheme = request.getScheme();....} else if (leadingSlash || !UriUtil.hasScheme(location)) {String scheme = request.getScheme();...} else {//啥也不干 直接返回return (location);}}
意思就是,需要重定向的话,Location里面的地址的Scheme根据request来,两者保持一致。
Shiro 重定向
属性http10Compatible
的值影响重定向的行为。
org.apache.shiro.web.util.RedirectView
protected void sendRedirect(HttpServletRequest request, HttpServletResponse response, String targetUrl, boolean http10Compatible) throws IOException {if (http10Compatible) {response.sendRedirect(response.encodeRedirectURL(targetUrl));} else {response.setStatus(303);response.setHeader("Location", response.encodeRedirectURL(targetUrl));}}
如果http10Compatible=true
,就把重定向的targetUrl的组装工作交给了servlet 容器处理,容器肯定是按照Servlet规范做了。
如果http10Compatible=false
,响应码是303
,并且Location
的值是一个相对地址。猜测是浏览器收到这个相对地址以后会自动拼接前面的http(s)://abc.com
,然后发起重定向。
Spring MVC 重定向
Spring MVC 中控制对Http 1.0 是否兼容的标识位是redirectHttp10Compatible
该属性在UrlBasedViewResolver
视图解析器内。
生效的地方依然是RedirectView
,类:org.springframework.web.servlet.view.RedirectView
相关代码:
protected void sendRedirect(HttpServletRequest request, HttpServletResponse response,String targetUrl, boolean http10Compatible) throws IOException {...//encodedURL /abc/tests/safa.htmlif (http10Compatible) {HttpStatus attributeStatusCode = (HttpStatus) request.getAttribute(View.RESPONSE_STATUS_ATTRIBUTE);if (this.statusCode != null) {response.setStatus(this.statusCode.value());response.setHeader("Location", encodedURL);}else if (attributeStatusCode != null) {response.setStatus(attributeStatusCode.value());response.setHeader("Location", encodedURL);}else {// Send status code 302 by default.response.sendRedirect(encodedURL);}}else {HttpStatus statusCode = getHttp11StatusCode(request, response, targetUrl);//303response.setStatus(statusCode.value());response.setHeader("Location", encodedURL);}}
如果redirectHttp10Compatible=true
,就把重定向的targetUrl的组装工作交给了servlet 容器处理,容器肯定是按照Servlet规范做了。
如果redirectHttp10Compatible=false
,响应码是303
,并且Location
的值是一个相对地址。猜测是浏览器收到这个相对地址以后会自动拼接前面的http(s)://abc.com
,然后发起重定向。
总结
到这里问题基本清楚了,来个总结吧。
Http10Compatible | Http10 No Compatible |
---|---|
Status Code :200Location :"${request.scheme}:\//domain.com/targetPath.html"
|
Status Code :303Location :"/targetPath.html"
|
结论很明显Http10Compatible
兼容与否,其实跟Http、Https并没有关系,只是恰巧出现的303状态码,以及Location里面存放的不在是完整的跳转url,而是一个/
开头的相对地址,协议的组装交给了浏览器处理。因此给大家了这种错觉,Https和Http的问题依然存在。
最佳实践
Tomcat有一个配置项:
public static class Tomcat {/*** Header that holds the incoming protocol, usually named "X-Forwarded-Proto".*/private String protocolHeader;
}
当请求通过nginx代理或者阿里云SLB转发的时候通过配置将请求protocol
放在X-Forwarded-Proto
Header 里面。后端容器就会根据协议在生成redirect Location采用相应的协议。
阿里云slb配置https重定向后变为http相关推荐
- 阿里云SLB配置HTPPS方式访问
1.http和htpps的区别 http: 默认端口:80 安全性: https: 默认端口:443 安全性:添加有加密证书,安全性相对较高 2.开始配置 1.slb负载均衡 在负载均衡实例列表中将服 ...
- 1 阿里云Nginx配置https实现域名访问项目
第一步:签署第三方可信任的 SSL 证书 证书可以直接在阿里云里面申请免费的ssl证书 登录阿里云账号,在上方搜索栏内搜索ssl,点击ssl证书(应用安全) 来到这个页面后点击购买证书 如图选择免费版 ...
- maven仓库 阿里云最新配置 https
maven镜像仓库替换成阿里云镜像仓库 安装好maven后,更新maven仓库的速度特别慢,或有有时候直接出现假死状态. 解决方案 在本地的maven的setting配置文件中添加阿里云镜像文件地址 ...
- 阿里云域名配置https(免费版)
登录阿里云找到自己的域名 开启SSL证书 选择购买两年以跳转到购买免费版页面 选择免费版,立即购买 购买成功,跳转证书控制台 申请证书 填写申请资料 按要求验证 验证成功,提交审核 Nginx配置证书 ...
- 阿里云nginx配置https
前段时间给自己的网站搭建了个https,之后又给公司的网站配置了https,配置时感觉记得不是很清晰了,特此记录一下. 步骤一: 申请ssl 证书,这里我用的是阿里云免费的证书,填写一些信息,就能申请 ...
- 阿里云SLB配置监听
添加https监听 1.添加监听,选择https,监听端口443,其他默认,下一步 2.选择域名对应的SSL证书,不开启双向认证,下一步 3.选择后端服务器组,没有的话可以新建一个,把要添加的服务器加 ...
- 阿里云SLB负载均衡配置方法(云起实验室)
阿里云SLB负载均衡实验 (云起实验室) 简介: 负载均衡的可以降低单台云服务器 ECS出现异常时对业务的冲击.其实就是多台服务器互为备胎,一台寄掉了换另一台.下面我简单说说怎么在阿里云上配置SLB负 ...
- 阿里云SLB上http强制跳转到https问题处理
背景: 最近一客户有一个需求,需要将外网所有http访问请求强制跳转到https,公网出口使用阿里云SLB,证书放在SLB上,SLB后端实例为ECS(webserver)web服务使用nginx, 网 ...
- 阿里云域名配置以及https证书(ssl证书)配置
阿里云域名配置以及https证书配置 目录: 一.tomcat 配置https 二.nginx 配置多个域名 最近开发小程序,小程序开发使用的所有接口都必须是https的 然后申请了阿里云服务器 申请 ...
最新文章
- 字节一面:如何从 100 亿 URL 中找出相同的 URL?
- python判断字符串
- docker操作运行一步一步来
- 1071svm函数 r语言_如何利用R语言中的rpart函数建立决策树模型
- asp 中使用Ftp.exe 上传大文件
- sqlserver死锁解决的存储过程
- 按15分钟取数据_Python爬取猫眼电影《飞驰人生》4万多条评论并对其进行数据分析...
- BizTalk动手实验(十七)ODBC适配器使用
- Adaboost算法的学习笔记~
- java session 生命周期_java之hibernate之session中对象的生命周期
- 联想启天m410进bios_联想启天M410台式机怎么装win7系统
- ubuntu安装nessus
- Vss、Vdd和Vcc
- date( 1day ) php,PHP_使用PHP的日期与时间函数技巧,PHP的日期时间函数date() 1,年- - phpStudy...
- oracle lag、lead函数
- 百度搜索:高效使用技巧
- P3084 [USACO13OPEN]照片Photo(差分约束)
- 苹果的AR真那么高科技?带你见识这些神奇AR应用
- java ftp服务器搭建教程_配置使用IIS的FTP服务器客户端实现 (Java)教程
- 阿里云ECS的优势有哪些?