一、AJAX
原理:
XMLHttpRequest对象
XHR使用步骤
创建XHR对象
const xhr = new XMLHttpRequest()
调用open方法,设置url和请求方法
xhr.open('请求方法','请求的url')
监听loadend事件,接受结果
xhr.addEventListener('loadend',() => {
console.log(xhr.response)
})
设置请求头
xhr.setRequestHeader('Content-Type','application/json')
调用send方法,发起请求
xhr.send('请求体数据')
使用示例:
const xhr = new XMLHttpRequest()
xhr.open('请求方法','请求的url')
xhr.addEventListener('loadend',() => {
//请求结果处理
console.log(xhr.response)
})
//请求头设置,请求体的类型
xhr.setRequestHeader('Content-Type','application/json')
//请求体
//......
xhr.send('需要发送的请求体数据')
二、axios
简易 axios 实现
function myAxios(config){
return new Promise((resolve,reject) => {
const xhr = new XMLHttpRequest()
//判断是否有 params 对象
if (config.params) {
//将 params 对象转为查询参数
const paramsObj = new URLSearchParams(config.params)
//将查询参数转为字符串
const queryString = paramsObj.toString()
//将查询参数加到 url 上
config.url += `?${queryString}`
}
xhr.open(config.method || 'get',config.url)
xhr.addEventListener('loadend', () => {
//返回的状态码在 200 到 300 之间为成功
if (xhr.status >= 200 && xhr.status < 300){
resolve(JSON.stringify(xhr.response))
} else {
reject(new error(xhr.response))
}
})
//判断是否有 data 参数
if (config.data) {
//指定发送的内容类型为 JSON
xhr.setRequestHead('Content-type','application/json')
//将对象数据转为 JSON
const params = JSON.stringify(config.data)
xhr.send(params)
}else {
xhr.send()
}
})
}
//使用
myAxios({
url: '目标源地址',
method: '请求方法',
params: {
}
}).then( resolve => {
//成功的结果处理
})
.catch( reject => {
//错误的结果处理
})
axios 的拦截器
axios 文件一般放在 util/request 下
基地址:
axios.defaults.baseURL = '请求地址'
请求拦截器:
axios.interceptors.request.use(function (config) {
const token = location.getItem('token')
token && (config.headers['token'] = token)
//发送请求之前做什么
return config
}, function (error) {
//对请求错误做什么
return Promise.reject(error)
})
响应拦截器:
axios.interceptors.response.use(function (response) {
const token = location.getItem('token')
token && (config.headers['token'] = token)
//对响应数据做什么
return response
}, function (error) {
//超出2xx的状态码都会触发该函数
//对响应错误做什么
if (error?.response?.status === '返回的状态码'){
//进行处理
}
return Promise.reject(error)
})
三、fetch
什么是 fetch ?
-
Fetch 被称之为下一代 Ajax 技术,内部采用 Promise 方式处理数据
-
API 语法简洁明了,比 XMLHttpRequest 更简单易用
-
采用模块化设计,API 分散多个对象中(如:Response对象、Request对象、Header对象)
-
通过数据流(Stream对象)处理数据,可以分块读取,有利于提高网站性能,对于大文件或者网速慢的场景极为有用
兼容性
- 不兼容 IE
使用 fetch 发送基本 get 请求
- 默认发送 get 请求,返回 Response 对象
语法
fetch(url)
.then(...)
.catch(...)
实例:
fetch('url').then(res => {
//res 为Response 对象,需要通过特定方法获取其中内容
//res.json() 是一个异步操作,表示取出所有内容,转为JSON对象并返回
return res.json()
}).then(json => {
//输出
console.log(json)
})
优化:
async function getData() {
try{
let res = await fetch('url')
let json = await res.json()
} catch (err){
console.log(err)
}
}
Response 对象
属性 | 含义 |
---|---|
res.ok | 返回一个布尔型,表示是否请求成功 |
ress.status | 表示HTTP回应的状态码 |
res.statusText | 返回状态码的文本信息(‘ok’) |
res.url | 返回请求的url地址 |
fetch 常见方法
方法 | 含义 |
---|---|
res.json() | 获得 JSON 对象 |
res.text() | 得到文本字符串 |
res.blob() | 得到二进制 blob 对象 |
res.formData() | 得到 FromData 表单对象 |
res.arrayBuffer() | 得到二进制 ArryBuffer 对象 |
fetch 配置参数
fetch 的第一个参数是 url ,此外还可以接收第二个参数,作为配置对象,自定义发送的HTTP请求
fetch(url, {
method: '',
headers:{
'Content-type': '数据格式:application/json'
},
body: '请求体数据'
})
fetch 发送 post 请求
基本语法:
发送的内容格式:
- json 格式:‘application/json’
- x-www-form-urlencoded 格式:‘application/x-www-form-urlencoded; charset=UTF-8’
- formData 格式
async function add(obj) {
let res = await fetch('url', {
method: '',
headers: {
'Content-type': 'application/json'
},
body: JSON.stringify(obj)
})
let json = await res.json()
return json
}
fetch 函数封装
目标效果:
http({
method: '',
url: '',
params:{...}
})
http({
method: '',
url: '',
data:{...}
})
封装后:
async function http(obj) {
//对象解构赋值
let {method, url, params, data} = obj
if (params) {
let UrlStr = new URLSearchParams(params).toString()
url += '?' + UrlStr
}
let res
if (data) {
res = await fetch(url, {
method: method,
headers: {
'Contents-Type': 'application/json'
},
body: JSON.stringify(data)
})
}else {
res = await fetch(url)
}
return res.json()
}
fetch 的缺点:
fetch 只对网络的请求报错,对 400 , 500 都当作成功的请求
三种方式的区别:
Ajax 实现了 局部数据刷新
本身是针对MVC的编程,多用于jquery项目,不符合现在前端MVVM的浪潮axios
基于Ajax封装
为MVVM框架而生 (vue react)
支持 Promise API
支持并发请求fetch
AJAX在ES6的替代品
fetch不是Ajax的进一步封装,而是原生js,没有使用XMLHttpRequest对象。
兼容性差