ajax
概述
js 中使用 ajax 不需要引用什么依赖 - 直接使用,通过事件 onreadystatechange 展现一个请求执行的每个阶段,在该函数的回调函数中通过属性 readyState 区分不同的阶段: 0表示创建 XMLHttpRequest 对象,即:new XMLHttpRequest()
1表示为异步对象设置了请求的参数,即:ajaxObj.open("get","请求后端的地址",true);
2表示异步对象已经发送请求,即:xhr.send();
3表示异步对象已经接受到数据,还没有解析
4表示异步对象已经解析完数据,可以使用了
在 readyState 等于4 的情况下还要 xhr.status 等于200 (表示后端成功返回了数据),才可正常获取数据,完整使用案例看下面代码:
菜鸟教程 -- 学的不仅是技术,更是梦想!!!
菜鸟教程 -- 学的不仅是技术,更是梦想!!!
菜鸟教程 -- 学的不仅是技术,更是梦想!!!
<!doctype html>
<html lang="zh">
<head>
<meta charset="utf-8">
<title>最简单 ajax 案例</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
</head>
<body>
<button onclick="printDate()">打印日期</button>
<button onclick="req()">请求后端数据</button>
<script type="text/javascript">
var ajaxObj = null;
window.onload = initCmpt;// 页面加载时初始化 ajax 对象
// 点击上面的按钮发送请求
function req(){
ajaxObj.open("get","https://www.jzy.world/wxbe/wechat/test",true);
ajaxObj.send();
}
// 初始化组件
function initCmpt(){
ajaxObj = new XMLHttpRequest();
ajaxObj.onreadystatechange = printReqState;
}
// ajax 对象每次状态变化都打印到浏览器控制台
function printReqState(){
switch(ajaxObj.readyState){
case 0: // 表示 new XMLHttpRequest()
printLog("还没有初始化异步对象");
break;
case 1:// 表示为异步对象设置了参数:ajaxObj.open("get","请求后端的地址",true); 第三个参数默认 true 表示异步执行,相反则是同步执行
printLog("初始化异步对象完毕");
break;
case 2:// 对应 ajaxObj.send();
printLog("异步对象发送请求完毕");
break;
case 3:
printLog("异步对象接受到数据还没有解析");
break;
case 4:
printLog("异步对象解析数据完毕");
// 正常接受到后端的数据的判断如下:
// if( ajaxObj.readyState == 4 && ajaxObj.status == 200 ) {
// var data = ajaxObj.responseText; 获取后端响应的数据
//}
if( ajaxObj.status == 200 ){
printLog("接收到的数据是:" + ajaxObj.responseText);
}
break;
default:
printLog("异步对象出现意料之外的状态");
}
}
function printDate(){
//const now = new Date().format2MilliSecond();
//const now = new Date().format2Second();
//const now = new Date().formatNoTime();
const now = new Date(new Date().setDate(new Date().getDate()+1)).format2MilliSecond();
console.log(now);
}
function printLog(content){
console.log(new Date().format2MilliSecond() + " : " + content);
}
/*
var ajaxObj = new XMLHtmlRequest();
ajaxObj.onreadstatechange = function () {
if( ajaxObj.readState == 1 ){
const now = new Date().format("yyyy-MM-dd HH:mm:ss.S");
console.log();
}
}
*/
/**
/*对Date的扩展,将 Date 转化为指定格式的String
/* 月(M)、日(d)、小时(h)、分(m)、秒(s)、季度(q) 可以用 1-2 个占位符,
/* 年(y)可以用 1-4 个占位符,毫秒(S)只能用 1 个占位符(是 1-3 位的数字)
/* 例子:
/* (new Date()).Format("yyyy-MM-dd HH:mm:ss.S") ==> 2019-01-02 10:19:04.423
/* (new Date()).Format("yyyy-M-d H:m:s.S") ==> 2019-1-2 10:19:4.18
/* yyyy-MM-dd HH:mm:ss ==> 2021-07-04 21:38:36
/* yyyy-MM-dd ==> 2021-07-04
*/
Date.prototype.format = function (fmt) {
var o = {
"M+": this.getMonth() + 1, //月份
"d+": this.getDate(), //日
"H+": this.getHours(), //小时
"m+": this.getMinutes(), //分
"s+": this.getSeconds(), //秒
"q+": Math.floor((this.getMonth() + 3) / 3), //季度
"S": this.getMilliseconds() //毫秒
};
if (/(y+)/.test(fmt)) fmt = fmt.replace(RegExp.$1, (this.getFullYear() + "").substr(4 - RegExp.$1.length));
for (var k in o)
if (new RegExp("(" + k + ")").test(fmt)) fmt = fmt.replace(RegExp.$1, (RegExp.$1.length == 1) ? (o[k]) : (("00" + o[k]).substr(("" + o[k]).length)));
return fmt;
}
Date.prototype.format2MilliSecond = function () {
const fmt = "yyyy-MM-dd HH:mm:ss.S";
return this.format(fmt)
}
Date.prototype.format2Second = function () {
const fmt = "yyyy-MM-dd HH:mm:ss";
return this.format(fmt)
}
Date.prototype.formatNoTime = function () {
const fmt = "yyyy-MM-dd";
return this.format(fmt);
}
// 调用方法
this.deliveryPlanDate = new Date().format("yyyyMMdd")
</script>
</body>
jquery
json方式
通过 JSON.stringfy 将参数对象序列化,后端 java 通过 @requestBody 读取参数,案例代码:
function login(){
$.ajax({
async: true,
//请求方式
type : "POST",
//请求的媒体类型
contentType: "application/json;charset=UTF-8",
// 这里后端使用了 springboot 中集成了 springsecurity做权限管理
data: JSON.stringify({"username":"1001","password":"7758"}),
//请求地址
url : "https://www.jzy.world/white/login/in",
//请求成功
success : function(result) {
console.log(result);
alert('登录返回的code=' + result.code + ',data=' + result.data);
},
//请求失败,包含具体的错误信息
error : function(e){
console.log(e.status);
console.log(e.responseText);
},
complete: function () {
// 旭纸业项目中通过 progress 锁定前端页面
// $.messager.progress({title: '提示', text: '请稍候...', interval: 5000});
// $.messager.progress('close');
}
})
}
对象方式
不需要声明 contentType,data 属性直接传入参数对象即可,后端 java 直接通过模型类接受数据(API方法中参数为模型类,前面不需要 @requestBody)
// 下面是前端代码
function login(){
$.ajax({
//请求方式
type : "POST",
data: paramObj,
//请求地址
url : "https://www.jzy.world/white/login/in",
//请求成功
success : function(result) {
console.log(result);
alert('登录返回的code=' + result.code + ',data=' + result.data);
},
//请求失败,包含具体的错误信息
error : function(e){
console.log(e.status);
console.log(e.responseText);
},
complete: function () {
// 旭纸业项目中通过 progress 锁定前端页面
// $.messager.progress({title: '提示', text: '请稍候...', interval: 5000});
// $.messager.progress('close');
}
})
}
// 下面是后端 java 代码
@RequestMapping(value = "/query", method = {RequestMethod.GET, RequestMethod.POST})
public List<Craftcolor> query(Craftcolor craftcolor) throws Exception {
List<Craftcolor> ret = service.query(craftcolor);
return ret;
}
deferred
从 1.5.0 版本开始,jquery 开始引入 deferred 对象,有点类似 Promise 对象。使得 ajax 请求可以使用链式形式的请求
$.ajax("test.html")
.done(function(){ alert("哈哈,成功了!"); })
.fail(function(){ alert("出错啦!"); });
或者下面的形式
$.ajax("test.html").then(
function(res){
// 请求成功响应.res是响应来的数据
},
function(err){
// 请求出现异常
}
)
Deffered 改造为 Promise 对象
const req1 = {type:'GET',dataType:'json',contentType: 'application/json',url: 'billType/selectCPCK',};
const req2 = {type:'GET',dataType:'json',contentType: 'application/json',url: 'jcStore/listQuery',};
const getAjaxPromise = function(option){
return new Promise(function(resolve,reject){
$.ajax({
type: option.type,
dataType: option.dataType,
contentType: option.contentType,
url: option.url,
data: option.data || '',
success: function(data){
resolve(data);
},
error: function(error){
reject(error);
}
});
})
}
const req1$ = getAjaxPromise(req1);
const req2$ = getAjaxPromise(req2);
req1$.then(
function(res){
console.log('req1$响应来的数据是:');
console.log(res);
return req2$;
},
function(err){
console.log('req1$请求出现异常:');
console.log(err);
}
)
.then(
function(res){
console.log('req2$响应来的数据是:');
console.log(res);
},
function(err){
console.log('req2$请求出现异常:');
console.log(err);
}
)
Promise.all 获取 promise对象
let generate = $.ajax({
url: 'productOrderBill/query/selectProductOrderPkByDtlPk',
data: {id: selected},
traditional: true,
dataType: 'json',
type: 'POST',
});
Promise.all([generate])
.then(data => {
if (data != undefined && data instanceof Array && data.length > 0) {
let g = data[0];
if (g.length <= 0 && m.length <= 0) {
$.messager.alert('提示', '无法查询相关入库单据!', 'warning');
}
for (let i of g) {
if (i) {
window.parent.addTab(`成品出库-${i}`, `cp_order_bill_picking?id=${i}`);
}
}
} else {
$.messager.alert('提示', '无法查询相关入库单据!', 'warning');
}
})
.finally(() => {
});
添加自定义header
$.ajax({
headers: {
"tradeuser":"o-huL5u73__97ihViycOniCmV_eI"
},
type: "POST",
url: "../../tradebe/sampleMain/save",
contentType: "application/json",
data: formData,
processData: false,
contentType: false,
async:false,
success: function (r) {
console.log('上传图片的响应结果:', r)
}
});
$.when
多个 http 请求并发执行,要求同时成功,否则进入第二个回调函数。第一个回调函数表示多个请求都成功了,按照前后顺序,res1 表示 req1的响应数据,res2 表示 req2 的响应数据。 注意响应来的对象 res1 的模型是:[data,statusText,jqXHR] 所以后台返回的实际数据是 res1[0]
const req1 = $.ajax({type:'GET',dataType:'json',contentType: 'application/json',url: 'billType/selectCPCK',});
const req2 = $.ajax({type:'GET',dataType:'json',contentType: 'application/json',url: 'jcStore/listQuery',});
// 注意下面传入函数名称,后面不要带有括号
$.when(req1,req2).then(
function(res1,res2){
console.log('请求成功返回:');
console.log(res1);
console.log(res2);
},
function(err){
console.log('请求出现异常:');
console.log(err);
}
)
超过2个以上的请求推荐使用下面方法
function getDataFun(){
var reqlist = [];
reqlist.push($.ajax({url: "/equip_rank",type:'GET',dataType:'jsonp'}));
reqlist.push($.ajax({url: "/score_rank",type:'GET',dataType:'jsonp'}));
reqlist.push($.ajax({url: "/billionaire_rank",type:'GET',dataType:'jsonp'}));
$.when.apply($,reqlist).then(function(data1,data2,data3){
//成功回调,所有请求正确返回时调用
console.log(data1[0]);
console.log(data2[1]);
console.log(data3[2]);
},function(){
//失败回调,任意一个请求失败时返回
console.log('fail!!');
})
}
