(1) 创建XMLHttpRequest
对象
所有现代浏览器 (IE7+、Firefox、Chrome、Safari 以及 Opera) 都内建了 XMLHttpRequest 对象
低版本IE中没有XMLHttpRequest
对象,我们需要创建AtiveXObject对象
let xhr;
if (window.XMLHttpRequest) {
xhr = new XMLHttpRequest; //IE7+,other
} else {
xhr = new ActiveXObject("Microsoft.XMLHTTP"); //IE6,IE5
}
(2)监听xhr对象的请求状态,当状态发生变化时,触发回调函数
readyState
:请求状态
0:请求未初始化
1: 服务器连接已建立
2: 请求已接收
3: 请求处理中
4: 请求已完成,且响应已就绪
xhr.onreadystatechange = function() {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
// 成功,通过responseText拿到响应的文本
let data = xhr.responseText;
data = JSON.parse(data);
console.log(data);
} else {
// 失败,根据响应码判断失败原因:
console.log(xhr.status);
}
} else {
// HTTP请求还在继续...
}
}
(3)配置请求信息
method:POST/GET, url, async:true/false
POST请求:
xhr.open("POST", reqParam.url, true);
// 设置请求头的contentType属性
xhr.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
GET请求:
xhr.open("GET", reqParam.url + '?test=test');
注:
(1)POST请求的参数在request的body中,GET请求的参数附在url后,以url?id=xxx&name=xxx
形式发送
(2)POST请求必须设置请求头的contentType属性
(3)GET请求有参数长度的限制,因为浏览器有对url的长度限制
(4)发送请求
xhr.send(null);
function ajax(reqParam) {
new Promise((resolve, reject) => {
let xhr;
if (window.XMLHttpRequest) {
xhr = new XMLHttpRequest;
} else {
xhr = new ActiveXObject("Microsoft.XMLHTTP");
}
function callback() {
if (xhr.readyState === 4) {
if (xhr.status === 200) {
let data = xhr.responseText;
data = JSON.parse(data);
resolve(data);
} else {
reject(xhr.status);
}
} else {
// HTTP请求还在继续...
}
}
if (reqParam.type.toUpperCase() === 'GET') {
xhr.onreadystatechange = callback;
xhr.open("GET", reqParam.url + '?test=test');
xhr.send(null);
} else if (reqParam.type.toUpperCase() === 'POST') {
xhr.onreadystatechange = callback;
xhr.open("POST", reqParam.url, true);
xhr.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
xhr.send(reqParam.data ? JSON.stringify(reqParam.data) : null);
} else {
reject({
flag: -1
});
}
}).then((res) => {
if (typeof reqParam['success'] === 'function') reqParam.success(res);
}, (res) => {
if (typeof reqParam['error'] === 'function') reqParam.error(res);
}).catch((res) => {
if (typeof reqParam['exception'] === 'function') reqParam.exception(res)
})
}
getMenuList() {
ajax({
url: '/mock/menu',
type: 'post',
data: {
test: 'test'
},
success: (response) => {
console.log(response);
if (response.flag === 1) {
let record = response.data;
if (record) {
let menus = toTreeData(record, '0', 'pId', 'menuId');
}
}
},
error: (response) => {
console.log(response)
}
})
}
$.ajax({
url: reqParam.url, // 发送请求的地址
data: JSON.stringify(reqParam.data) || JSON.stringify({}), // 发送到服务器的数据,JSON格式需要转换为字符串
async: reqParam.async === undefined ? true : reqParam.async, // 默认设置下,所有请求均为异步请求
type: reqParam.type ? reqParam.type : 'POST',
contentType: 'application/json; charset=UTF-8', // 发送信息至服务器时内容编码类型,默认值: "application/x-www-form-urlencoded"
dataType: 'json', // 预期服务器返回的数据类型
cache: false,
// 失败回调函数,返回jqXHR对象,响应状态和异常信息
error: function (jqXHR, textStatus, errorThrown) {
console.log(textStatus);
},
// 成功回调函数,返回响应数据,响应状态和jqXHR对象
success: function (data, textStatus, jqXHR) {
let res = data;
}
})
fetch是ES6中新增的一种Http数据请求方式,它相比原生的XMLHttpRequest更具有可扩展性和高效性。
// fetch无法对服务器响应进行异常抛出,需要在内部自行判断
function checkStatus(response) {
if (response.status >= 200 && response.status < 300) {
return response;
}
const error = new Error(response.statusText);
error.response = response;
throw error;
}
export function request(reqParam) {
return fetch(reqParam.url,
{
method: reqParam.type ? reqParam.type : 'POST',
// POST请求发送参数在body中,GET需要拼接在URL后
body: JSON.stringify(reqParam.data)
})
.then(checkStatus)
.then((res) => {
if (typeof reqParam['success'] === 'function') reqParam.success(res.json())
}, (res) => {
if (typeof reqParam['error'] === 'function') reqParam.error(res);
})
.catch((res) => {
if (typeof reqParam['exception'] === 'function') reqParam.exception(res)
});
}