Nginx反向代理解决浏览器跨域问题

在nginx.conf中添加此配置

1
2
3
4
5
6
7
8
9
10
11
12
13
server {
 
    listen       80;
    server_name  apisina.com;
    charset utf-8;
    add_header Access-Control-Allow-Origin *;
    add_header Access-Control-Allow-Headers Origin,X-Requested-Width,Content-Type,Accept;
    add_header Access-Control-Allow-Methods GET,POST,PUT,DELETE,OPTIONS;
 
    location / {
        proxy_pass   https://api.weibo.com/2/statuses/share.json;
   }
}

解释:

http://apisina.com是你拥有的域名, 即被你的nginx解析的域名, nginx如上设置了Access-Control的header后, 你能够跨域访问该域名

https://api.weibo.com/2/statuses/share.json是新浪的API接口, 浏览器因为跨域限制, 而新浪没有设置header, 所以不能直接访问

所以需要浏览器先访问http://apisina.com, 然后nginx收到请求后, 代理到新浪的接口, 就可以解决跨域问题了

那么问题来了, 为什么要使用反向代理而不是用redirect跳转至该域名呢?

原因很简单, redirect是301跳转, 所有请求方式都会变成get方式, 也就是说POST经过跳转后变成GET, 还是无法访问该接口

而且最重要的一点, 就算跳转至新浪的域名, 也是在浏览器中跳转, 跳转之后继续被跨域限制, 无法访问, 所以必须使用反向代理实现该需求

扩展:

同样类似的还有80端口重定向至443端口的问题, 如果将80端口重定向至443端口, 那么所有访问http的请求在经过nginx跳转至https后会变成get请求, 如果接口中要求POST请求, 则服务端会收不到正确的请求, 就会出现此问题, 那么解决办法只能是在转发的时候抛出一个307状态码

nginx配置如下:

1
2
3
4
5
6
7
server {
 
    listen       80;
    server_name  www.baidu.com;
 
    return 307 https://www.baidu.com;
}

当访问http://www.baidu.com时, 利用307状态码跳转至https://www.baidu.com, 则不会出现请求方式全被转换为get方式的问题

关于301状态码 与 307状态码的解释

301 Moved Permanently

被请求的资源已永久移动到新位置,并且将来任何对此资源的引用都应该使用本响应返回的若干个 URI 之一

307 Temporary Redirect

请求的资源现在临时从不同的URI 响应请求。由于这样的重定向是临时的,客户端应当继续向原有地址发送以后的请求

从上面我们可以看出,301跳转是永久重定向,而307是临时重定向。这就是301跳转与307跳转两者之间的区别

发布评论
还没有评论,快来抢沙发吧!