一、说明
原生js提供了两种数据请求方式fetch,ajax
- ajax需要封装的, fetch不需要
- ajax不太符合MV* 开发方式,fetch可以认为是js为了MV*方式做的量身打造
- fetch也是Promise
功能:用fetch请求动态数据
1、get请求
(1)不带参数
1 // 通过fetch获取百度的错误提示页面
2 fetch('https://www.baidu.com/search/error.html') // 返回一个Promise对象
3 .then((res)=>{
4 return res.text() // res.text()是一个Promise对象
5 })
6 .then((res)=>{
7 console.log(res) // res是最终的结果
8 })
(2)带参数:
get请求参数是连接在url上
1 methods: {
2 get () {
3 fetch(`${ BASE_URL }/get.php?a=1&b=2`)//get请求参数是连接在url上
4 .then( data => data.text() )
5 .then( res => {
6 this.num = res
7 })
8 .catch( err => console.log( err ))
9 },
method: 'GET'不写默认是get请求
2、post请求
(1)不带参数
1 // 通过fetch获取百度的错误提示页面
2 fetch('https://www.baidu.com/search/error.html', {
3 method: 'POST' // 指定是POST请求
4 })
5 .then((res)=>{
6 return res.text()
7 })
8 .then((res)=>{
9 console.log(res)
10 })
(2)带参数
post请求传递参数:
body: new URLSearchParams([["a", 1],["b", 2]]).toString()
注意:POST请求的参数,一定不能放在URL中,这样做的目的是防止信息泄露。
1 post () {
2 /*
3 1. post请求参数如何携带
4 */
5 fetch(`${ BASE_URL }/post.php`,{
6 method: 'POST',
7 // body: JSON.stringify({
8 // a: 1,
9 // b: 2
10 // })
11 headers: new Headers({
12 'Content-Type': 'application/x-www-form-urlencoded' // 指定提交方式为表单提交
13 }),
14 body: new URLSearchParams([["a", 1],["b", 2]]).toString()
15 }).then( data => data.text() )
16 .then( res => {
17 this.sum = res
18 })
19 .catch( err => console.log( err ))
20 },
总结:
fetch( url, config ).then().then().catch()
1 getMovies () {
2 /* 第一个then是为数据格式化,可以格式化的数据类型有: json text blob[ 二进制 ]
3 第二个then才是得到的数据
4 */
5 // fetch( url, config ).then().then().catch()
6
7 fetch('./mock/movie.json')
8 .then( data => data.json() )
9 .then( res => {
10 console.log("兵哥: getMovies -> res", res)
11 this.movies = res.movieList
12 })
13 }
得到json格式数据:
1 // 通过fetch获取百度的错误提示页面
2 fetch('https://www.baidu.com/rec?platform=wise&ms=1&rset=rcmd&word=123&qid=11327900426705455986&rq=123&from=844b&baiduid=A1D0B88941B30028C375C79CE5AC2E5E%3AFG%3D1&tn=&clientWidth=375&t=1506826017369&r=8255', { // 在URL中写上传递的参数
3 method: 'GET',
4 headers: new Headers({
5 'Accept': 'application/json' // 通过头指定,获取的数据类型是JSON
6 })
7 })
8 .then((res)=>{
9 return res.json() // 返回一个Promise,可以解析成JSON
10 })
11 .then((res)=>{
12 console.log(res) // 获取JSON数据
13 })
格式化数据:
data.json()
data.text()
处理数据可以使用querystring
1 const qs = require( 'querystring' )
2 const str = 'a=1&b=2'
3 const obj = { a: '1', b: '2' }
4 console.log( qs.parse( str ))
5 console.log( qs.stringify( obj ))
强制带Cookie:
1 // 通过fetch获取百度的错误提示页面
2 fetch('https://www.baidu.com/search/error.html', {
3 method: 'GET',
4 credentials: 'include' // 强制加入凭据头
5 })
6 .then((res)=>{
7 return res.text()
8 })
9 .then((res)=>{
10 console.log(res)
11 })
二、fetch的封装
1 /**
2 * 将对象转成 a=1&b=2的形式
3 * @param obj 对象
4 */
5 function obj2String(obj, arr = [], idx = 0) {
6 for (let item in obj) {
7 arr[idx++] = [item, obj[item]]
8 }
9 return new URLSearchParams(arr).toString()
10 }
11
12 /**
13 * 真正的请求
14 * @param url 请求地址
15 * @param options 请求参数
16 * @param method 请求方式
17 */
18 function commonFetcdh(url, options, method = 'GET') {
19 const searchStr = obj2String(options)
20 let initObj = {}
21 if (method === 'GET') { // 如果是GET请求,拼接url
22 url += '?' + searchStr
23 initObj = {
24 method: method,
25 credentials: 'include'
26 }
27 } else {
28 initObj = {
29 method: method,
30 credentials: 'include',
31 headers: new Headers({
32 'Accept': 'application/json',
33 'Content-Type': 'application/x-www-form-urlencoded'
34 }),
35 body: searchStr
36 }
37 }
38 fetch(url, initObj).then((res) => {
39 return res.json()
40 }).then((res) => {
41 return res
42 })
43 }
44
45 /**
46 * GET请求
47 * @param url 请求地址
48 * @param options 请求参数
49 */
50 function GET(url, options) {
51 return commonFetcdh(url, options, 'GET')
52 }
53
54 /**
55 * POST请求
56 * @param url 请求地址
57 * @param options 请求参数
58 */
59 function POST(url, options) {
60 return commonFetcdh(url, options, 'POST')
61 }
62 GET('https://www.baidu.com/search/error.html', {a:1,b:2})
63 POST('https://www.baidu.com/search/error.html', {a:1,b:2})