为了复现访问http接口时,浏览器内部307跳转到https的情况,我尝试本地服务器模拟浏览器行为。
先创建下面文件:
openssl.cnf
[req]
prompt=no
distinguished_name = req_distinguished_name
req_extensions = v3_req
[req_distinguished_name]
C=ZH
ST=China
L=ShangHai
O=Treemonster Self-signed place
OU=Treemonster Self-signed place
CN=Chen.wg1993
[ v3_req ]
# Extensions to add to a certificate request
basicConstraints = CA:FALSE
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
subjectAltName = @alt_names
[alt_names]
DNS.1 = plat-gw.jd.com
IP.1 = 127.0.0.1
svr.js
fs=require('fs')
require('http').createServer((req, res)=>{
res.writeHead(307, {
'Access-Control-Allow-Credentials': true,
'Access-Control-Allow-Origin': 'http://wuxian.shop.jd.com',
'Location': 'https://plat-gw.jd.com/',
'Non-Authoritative-Reason': 'HSTS',
})
res.end()
}).listen(80)
require('https').createServer({
key: fs.readFileSync('./server-key.pem'), // 直接用ca-key, ca-cert也是可以的,但是ca从逻辑上是证书颁发机构,其签发的才是应用证书,所以不直接用
cert: fs.readFileSync('./server-cert.pem'),
server
}, (req, res)=>{
res.writeHead(200, {
'Access-Control-Allow-Credentials': true,
'Access-Control-Allow-Origin': 'null',
})
res.end('ok'+req.rawHeaders)
}).listen(443)
命令生成证书
# 生成证书颁发机构的证书
openssl genrsa -out ca-key.pem
openssl req -new -key ca-key.pem -config openssl.cnf -out ca-csr.pem
openssl x509 -req -in ca-csr.pem -signkey ca-key.pem -out ca-cert.pem
# 生成应用证书
openssl genrsa -out server-key.pem 2048
openssl req -new -key server-key.pem -config openssl.cnf -out server-csr.pem
openssl x509 -req -CA ca-cert.pem -CAkey ca-key.pem -CAcreateserial -signkey server-key.pem -in server-csr.pem -out server-cert.pem -extfile openssl.cnf
加hosts
127.0.0.1 plat-gw.jd.com
启动node
node svr.js
先在浏览器打开一次 http://plat-gw.jd.com
一开始隐藏详情按钮显示的是"高级",点一次之后展开了详情,再点最下面的继续前往,让浏览器记住这个证书允许访问。
然后进到调试页面控制台,先尝试 'Access-Control-Allow-Origin': 'sb',发现果然浏览器拒绝了连接。然后尝试null,请求成功,再尝试 * 发现也是可以的,所以这种情况只要服务端增加Origin: null的处理逻辑即可。
除此之外更好的方法应该是运维层添加强制页面https跳转,不允许http访问,那么就不会有这种307的情况发生了。
当然代码中直接写https接口也是可以避免这个问题的,但从逻辑上这么做是不对的,因为用户http协议去访问网站,理应页面上的接口也是http调用的,而不是https。
相关文档
暂无
随便看看
畅言模块加载中