fetch是一种可代替 ajax 获取/提交数据的技术,有些高级浏览器已经可以window.fetch使用了。相比于使用 jQuery.ajax 它轻量(只做这一件事),而且它原生支持 promise ,更加符合现在编程习惯。
npm install whatwg-fetch --save
,即可安装,为了兼容老版本的浏览器,还需要安装npm install es6-promise --save
fetch(url,init).then(function(response) { } )
参数:
url代表要获取的资源,可能值是一个url或者一个Request对象
init: 可选,是一个对象,参数有
method: 请求使用的方法get或者post
headers: 请求头信息,是一个对象
headers: {
"Content-Type": "application/json"
},
body: 请求的 body 信息:可能是一个 Blob、BufferSource、FormData、URLSearchParams 或者 USVString 对象。注意 GET 或 HEAD 方法的请求不能包含 body 信息。
mode: 请求的模式,如 cors、 no-cors 或者 same-origin,默认为no-cors,该模式允许来自 CDN 的脚本、其他域的图片和其他一些跨域资源,但是首先有个前提条件,就是请求的 method 只能是HEAD、GET 或 POST。此外,如果 ServiceWorkers 拦截了这些请求,它不能随意添加或者修改除这些之外 Header 属性。第三,JS 不能访问 Response 对象中的任何属性,这确保了跨域时 ServiceWorkers 的安全和隐私信息泄漏问题。cors模式允许跨域请求,same-origin模式对于跨域的请求,将返回一个 error,这样确保所有的请求遵守同源策略。
credentials: ‘include’ //表示跨域是可以带cookie的(fetch跨域请求默认不会带cookie,需手动指定这个参数)
cache: 请求的 cache 模式: default, no-store, reload, no-cache, force-cache, or only-if-cached.
返回值:一个 Promise,resolve 时回传 Response 对象。
get的基本使用
首先引入依赖的插件
import 'whatwg-fetch'
import 'es6-promise'
var result = fetch('/api/1', {
credentials: 'include',
headers: {
'Accept': 'application/json, text/plain, */*'
}
});
fetch( )方法请求数据,返回的是一个promise对象,下来就可以使用promise的语法结构
result.then(res=>{
return res.text()
}).then(text=>{
console.log(text)
})
result.then(res=>{
return res.json()
}).then(json=>{
console.log(json)
})
注意,以上两个用法中,只有res.text( )和res.json( )是不一样的,这两个方法就是将返回的Response 数据转换成 字符串 或者 json格式
post的基本使用
import 'whatwg-fetch'
import 'es6-promise'
var result = fetch(url,{
method:'post',
credentials: 'include',
headers:{
'Accept': 'application/json, text/plain, */*',
'Content-Type': 'application/x-www-form-urlencoded'
},
body: "a=100&b=200"
})
fetch 提交数据之后,返回的结果也是一个promise对象,跟get方法一样,所以处理方式也一样
抽象post和get
如果每次获取数据,都会像上面一样写好多代码,太冗余了。我们可以将get和post分为两个方法抽象出来,分为两个js文件
get.js
import "whatwg-fetch"
import "es6-promise"
export function get(url){
var result = fetch(url,{
credentials:"include",
headers:{
'Accept':'application/json,text/plain,*/*'
}
});
return result;
}
post.js
import "whatwg-fetch"
import "es6-promise"
// 将对象拼接成 key1=val1&key2=val2&key3=val3 的字符串形式
function obj2params(obj){
var result = "";
var item;
for(item in obj){
result += '&'+ item + '=' + encodeURIComponent(obj[item]);
}
//因为result第一个参数是 & 所以需要去掉
if(result){
result = result.slice(1);
}
return result;
}
// 发送 请求
export function post(url,paramsObj){
var result = fetch(url,{
method:'POST',
credentials:'include',
headers:{
'Accept':'appliaction/json,text/plain,*/*',
'Content-Type':'application/x-www-form-urlencoded'
},
body:obj2params(paramsObj)
});
return result;
}
需要注意的是,在post.js
中,将参数做了处理,因为上面的代码中提到,body: “a=100&b=200”这种参数格式是有要求的,而我们平时在js中,最多用到的就是JSON格式的数据,因此需要转一下
这两个方法抽象出来,在从其他组件中调用就变的很简单了
安装,我们使用的是koa
来做后端接口的模拟,因此需要安装koa以及相关的插件npm install koa koa-body koa-router --save-dev
,注意这里使用–save-dev,意思是我们只在开发过程中使用 koa ,项目发布之后 koa 就没用了。因为发布之后的项目,使用的就是后端工程师开发的线上的接口,而不是我们基于 koa 写的接口。
即自己用一个 web 框架,按照既定的接口和数据结构的要求,自己模拟后端接口的功能,让前端项目能顺利跑起来。该方式适用于新开发的项目,后端和前端同时开发。
我们将模拟接口的代码写在./mock
目录下,接口文件是./mock/server.js
(开发真正的项目时,会分成多个不同的模块)
注意:在package.json中需要增加如下代码,然后npm run mock
即可启动模拟的接口服务
"scripts": { "mock": "node --harmony ./mock/server.js", },
使用webpack-dev-server的代理
koa 接口的端口是3000,而我们项目的接口是8080,这样不就跨域了吗?————如果默认情况下,肯定是跨域了。此时就需要 webpack-dev-server 做一个代理的转发。配置代码在./webpack.config.js中
devServer: {
proxy: {
// 凡是 `/api` 开头的 http 请求,都会被代理到 localhost:3000 上,由 koa 提供 mock 数据。
// koa 代码在 ./mock 目录中,启动命令为 npm run mock
'/api': {
target: 'http://localhost:3000',
secure: false
}
},
contentBase: "./public", //本地服务器所加载的页面所在的目录
colors: true, //终端中输出结果为彩色
historyApiFallback: true, //不跳转
inline: true, //实时刷新
hot: true // 使用热加载插件 HotModuleReplacementPlugin
}