ECMAScript 2015(ES6) 标准的发布已经三年有余,现代浏览器对ES6语法的支持趋于完善,用Promise对象处理异步请求被越来越多的开发者应用。为了更好地处理异步请求,作为对现有的XMLHttpRequest方法的替代,JavaScript引入了fetch方法,基于Promise处理异步请求。在Fetch出现之前我们发送异步请求默认都是通过ajax,底层使用了宿主环境的(XHR)XMLHTTPRequest 对象来实现异步请求。实现代码如下:
var xhr = new XMLHttpRequest();xhr.open("get","example.php", true);xhr.send(null);xhr.onreadystatechange = function(){ if(xhr.readyState === 4){ if(xhr.status == 200){ alert(xhr.responseText); } }}
当然我们一般会用一些封装过的ajax实现解决传统方式的繁琐写法以及xhr低版本浏览器可能出现的兼容问题,比如jquery的ajax:
$.ajax({ url: 'example.asp', type: 'get', success: function(){ }})
Fetch API 提供了一个 JavaScript接口,用于访问和操纵HTTP管道的部分,例如请求和响应。它还提供了一个全局 fetch()方法,该方法提供了一种简单,合理的方式来跨网络异步获取资源。
fetch的基本用法
fetch('http://example.com/movies.json') .then(function(response) { return response }) .then(function(response) { console.log(response); });
是不是看上去和jquery以及一些流行的框架的http库很相似。但是你不要忘了,fetch是浏览器原生支持的,使用fetch可以不用引用http的类库即可实现。fetch默认返回 一个promise对象。非支持async 和await,使用它可以更加简洁的编写我们的http请求逻辑。
注意点:
1.fetch是有兼容问题的
IE系列是完全不支持的,主流浏览器的早起版本也不支持,所以如果在项目中使用需要做兼容方案处理。
2.fetch 不管请求处理成功还是失败,都会触发promise的resolve状态回掉。这个和传统的ajax 框架是有点区别的。fetch只有当网络故障导致请求发送失败或者跨域的时候才会触发reject的逻辑。我们可以通过response 对象的ok是否是true来判断是否是真正的成功。
fetch('flowers.jpg').then(function(response) { if(response.ok) { return response.blob(); } throw new Error('Network response was not ok.');}).then(function(myBlob) { var objectURL = URL.createObjectURL(myBlob); myImage.src = objectURL; }).catch(function(error) { console.log('There has been a problem with your fetch operation: ', error.message);});
3.fetch配置请求是否携带cookie和接受服务端写入cookie是通过设置credentials
// 所有情况都携带cookiefetch('https://example.com', { credentials: 'include' })// 目前改为默认是same-origin// 同源的情况下带cookiefetch('https://example.com', { credentials: 'same-origin' })// 忽略cookiefetch('https://example.com', { credentials: 'omit' })
4.fetch不想xhr可以原生支持异步请求,fetch因为默认是一个promise的对象。所以如果想用同步的写法,可以借助async await 来实现。
async function getInfo(){ const res = await fetch('http://www.test.asp'); const result = await res; return result;}
Fetch更多参数
fetch(url, { body: JSON.stringify(data), // must match 'Content-Type' header cache: 'no-cache', // *default, no-cache, reload, force-cache, only-if-cached credentials: 'same-origin', // include, same-origin, *omit headers: { 'user-agent': 'Mozilla/4.0 MDN Example', 'content-type': 'application/json' }, method: 'POST', // *GET, POST, PUT, DELETE, etc. mode: 'cors', // no-cors, cors, *same-origin redirect: 'follow', // manual, *follow, error referrer: 'no-referrer', // *client, no-referrer })
需要注意的是,该语法是比较新的用法,浏览器的支持可能会随着升级产生一些变化。所以切记做好兼容探测处理。避免意外出现。