淘先锋技术网

首页 1 2 3 4 5 6 7

在Web开发中,http跨域是一个很常见的问题,特别是在使用JavaScript进行客户端编程时更是如此。http跨域简单来说就是浏览器不能直接向不同源(域名、协议、端口号)的服务器发送请求,这种限制称为同源策略。

假设我们的网站是www.abc.com,而我们在网站中需要访问另外一个域名为www.xyz.com的后端API,我们会发现浏览器无法请求到对应的API数据并得到一个错误提示

Access to XMLHttpRequest at 'http://www.xyz.com/api/getdata' from origin 'http://www.abc.com' 
has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.

这个错误提示的原因是浏览器的同源策略禁止我们的JavaScript通过ajax请求到不同源的服务器。

那么我们该如何在JavaScript代码中跨域请求数据呢?下面介绍几种解决方案。

JSONP

JSONP的全称是JSON with Padding,它利用script标签可以跨域访问资源的特性进行跨域数据请求。

let script = document.createElement('script');
script.src = 'http://www.xyz.com/abc?callback=parseData';
document.body.appendChild(script);
function parseData(data){
// 处理接收到的数据
}

通过注入一个script标签重新加载数据来实现jsonp跨域请求,但是jsonp只能发送GET请求。

CORS

CORS是Cross-Origin Resource Sharing的缩写,它是一种可以允许跨域请求的机制。

在服务器端,只需要在请求响应中添加一些HTTP头信息即可允许前端跨域访问。

Access-Control-Allow-Origin:表示允许哪些源请求; 
Access-Control-Allow-Methods: 表示允许请求的方法; 
Access-Control-Allow-Headers: 表示允许请求的自定义header; 
Access-Control-Max-Age:表示对请求的响应进行缓存的时间长度(以秒为单位)。

如果我们的API服务器允许跨域访问,添加头信息到响应中即可:

Access-Control-Allow-Origin: *  // 表示允许所有域名进行跨域访问
Access-Control-Allow-Methods: GET, POST, PUT, DELETE
Access-Control-Allow-Headers: Content-Type, Authorization

window.postMessage

window.postMessage可以进行跨iframe和跨窗口的通信,但是它需要在对应的窗口或iframe中定义一个监听函数。

假如我们的父窗口在页面中包含一个子iframe,子iframe中的脚本就可以使用postMessage与父窗口进行通信。

// iframe.html页面代码
window.parent.postMessage("Hello, parent", "*");
// 父窗口
window.addEventListener("message", function(event){
if (event.source != window) return;
if (event.data == "Hello, parent") parentFunction();
});

后台代理模式

有时候某些API服务器不允许跨域访问,那么我们可以通过后台代理模式来实现:

在我们的Web服务器上,我们可以写一个中间代理程序来接收前端发送的请求,并将其转发给API服务器。

在这种模式下,我们的前端代码不直接访问API服务器,而是向我们的代理服务器发送请求,代理服务器将请求重定向到API服务器。API服务器将响应返回给代理服务器,代理服务器再将响应返回到前端页面。

以上是几种常见的跨域请求解决方案,但是需要注意的是,每种方案都有各自的优缺点,开发者需要根据项目需求和实际情况选择。