jQuery中ajax的简单实现
ajax的使用
$.ajax( {
url: '../test/test.css',
dataType: 'style',
timeout: 5,
success: function( data ) {
console.log( data );
console.log( typeof data );
},
error: function( msg ) {
console.log( msg );
}
} );
分析:
- 给jQuery传入一个参数配置对象,对象属性是可选的,那就说明是有默认配置的
- 需要在内部把传入的data转换成url参数的连接方法,key=value&key2=value2。
- 对于get和post的不同,请求url也需要做判断处理。
代码解析
设置ajax默认配置参数
/** * ajax请求的默认配置 * @type {属性对象} */ ajaxSettings:{ url:location.href, //默认的url地址 type:'POST', //默认的请求方式 dataType:'JSON', //默认的返回数据类型 contentType:'application/x-www-form-urlencoded;charset=utf-8', //post方法httpheader设置内容 timeout:null, //默认超时时间 async:true, //默认异步请求 success:function(){}, //成功请求回调 complete:function(){}, //完成请求回调(不管成功还是失败) error:function(){} //请求出现错误回调 },
将对象转变成url参数形式
/** * 将对象转变成url参数形式的字符串 * @param {object} data 对象 * @return {string} url参数形式的字符串 * key=value&key2=value2 */ urlStringify:function(data){ var result = ''; if (!jQuery.isObject(data)) { return result; } for (var key in data){ //统一编码 防止汉字出现乱码 result += window.encodeURIComponent(key)+'='+window.encodeURIComponent(data[key])+'&'; } //将最后一个&字符去掉 return result.slice(0,-1); },
处理传入的配置和默认的配置
/** * 处理ajax传入的配置 * @param {objecr} options ajax传入的配置 * @return {对象} 处理好之后的配置 */ processOptions:function(options){ var newOptions = {}; //这里修改extend方法,当只有一个参数时,将参数添加到自身,多个参数时,将后面的参数添加到第一个参数中。 jQuery.extend(newOptions,jQuery.ajaxSettings,options); //开始处理传入的数据,data将对象变成字符串 newOptions.data = jQuery.urlStringify(newOptions.data); //将方法 get和post换成大写字母,方便后面进行判断 newOptions.type = newOptions.type.UpperCase(); if (newOptions.type === 'GET') { newOptions.url = newOptions.url +'?'+newOptions.data; //此处将data设为null,那么在ajax.send()时,就可以直接将data作为参数传入。 newOptions.data = null; } return newOptions; },
ajax方法
/** * ajax方法 * @param {obj} options 包含ajax请求配置 * @return {请求返回的数据} 按照传输的格式进行返回处理 */ ajax:function(options){ //定义返回结果变量和定时器变量 var reuslt ,timer; var xhj = new XMLHttpRequest(); //合并默认配置和传入配置 var optionNew = jQuery.processOptions(options); xhj.open(optionNew.type,optionNew.url,optionNew.async); //post方法时,设置httprequestHeader的content-type属性 if (optionNew.type === 'POST') { xhj.setRequestHeader('content-type',optionNew.contentType); } xhj.onreadystatechange = function(){ if (xhj.readyState === 4) { //ajax请求已经完成,此时停止定时器 clearTimeout(timer); optionNew.complete(); if (xhj.status >= 200 && xhj.status <300 || xhj.status == 304) { //根据不同类型进行判断 switch (dataType) { case 'JSON':{ //JSON解析 result = JSON.parse(xhj.responseText); } break; case 'script':{ //执行script字符串代码 eval( xhj.responseText ); result = responseText; } break; case 'style':{ //新建一个style标签,并且添加到head标签中 $('<style><style/>').html(xhj,responseText).appendTo('head'); resutl = xhj.responseText; } break; default:{ result = xhj.responseText; } break; } //请求成功,将处理结果返回 optionNew.success(result); }else { //请求失败,将ajax的当前状态返回,方便进行判断 optionsNew.error(xhj.status); } } }; //如果设置了超时,那么开启定时器进行处理,超时后提醒超时 if (optionNew.timeout) { timer = setTimeout(function(){ optionNew.error('超时'); //时间超时,事件回调就没有必要继续执行了 xhj.onreadystatechange = null; },optionsNew.timeout); } xhj.send(optionNew.data); },