需求场景:借助 ajaxTransport 来自定义扩展功能。
项目需求:jQuery 版本: 1.10.2,错误打点,发起 jsonp 请求发生错误的时候前端需要向打点地址发送一个请求。
-
简单演示:
测试代码:$.ajax('http://google.com/a.js',{ type: 'GET',dataType: 'jsonp',success: function(success,statusText,jqXHR){ console.log('jsonp request success'); },error: function(jqXHR,error){ console.log('jsonp error'); } }); 由于 1.10.2 版本的 jquery 并没有对创建的 script 监听错误事件,故无法调用 error 方法,故无法进一步将前端信息错误上报
解决方案:
$.ajaxTransport('+script',function(s){ // This transport only deals with cross domain requests var script,head = document.head || $('head')[0] || document.documentElement; return { send: function(_,callback) { script = document.createElement('script'); script.async = true; if(s.scriptCharset){ script.charset = s.scriptCharset; } script.src = s.url; // Handle error script.onerror = function(err){ // Handle memory lead in IE script.onload = script.onreadystatechange = null; script.onerror = null; // Remove the script if(script.parentNode){ script.parentnode.removeChild(script); } // Dereference the script script = null; if(err.type === 'error'){ callback(404,err.type); } } // Attach handlers for all browsers script.onload = script.onreadystatechange = function(_,isAbort){ if(isAbort || !script.readyState || /loaded|complete/.test(script.readyState)){ // Handle memeory leak in IE script.onload = script.onreadystatechange = null; // Remove the script if(script.parentNode){ script.parentNode.removeChild(script); } // Dereference the script script = null; // Callback if not abort if(!isAbort){ callback(200,'success'); } } }; // Cicumvent IE6 bugs with base elements (#2709 and #4378) by prepending // Use native DOM manipulation to avoid our domManip AJAX trickery head.insertBefore(script,head.firstChild); },abort: function(){ if(script){ script.onload(undefined,true); } } }; });
需求场景:借助 ajaxSetup 新增 dataType.
-
简单演示:
解决方案:function parseYaml(text){ console.log('You are parsing yaml file!'); return 'yaml' + text + 'yaml'; } $.ajaxSetup({ accepts: { yaml: 'application/x-yaml,text/yaml' },contents: { yaml: /yaml/ },converters: { 'text yaml': function(text){ return parseYaml(text); } } });
测试代码:
// 发送 dataType 为 yaml 的请求 $.ajax({ url: 'http://google.com/helloworld.yaml',dataType: 'yaml',success: function(data){ console.log(data); } });
需求场景:借助 ajaxPrefilter 来自定义扩展功能。
项目需求:防止 ajax 请求的重复提交
-
简单演示:
解决方案:
var pendingRequests = {};function storePendingRequest(key,jqXHR){
pendingRequests[key] = true; jqXHR.pendingRequestKey = key;
}
function generatePendingRequestKey(options){
return (options.type + options.url + options.dataType).toLowerCase().replace(/[^a-z0-9]/g,'');
}
$.ajaxPrefilter(function( options,originalOptions,jqXHR ) {// 不重复发送相同请求 var key = generatePendingRequestKey(options); if (!pendingRequests[key]) { storePendingRequest(key,jqXHR); } else { // or do other jqXHR.abort(); } var complete = options.complete; options.complete = function(jqXHR,textStatus) { // clear from pending requests pendingRequests[jqXHR.pendingRequestKey] = null; if ($.isFunction(complete)) { complete.apply(this,arguments); } };
});
测试代码:
for(var i = 0; i < 10; i++){var j = 0; $.ajax({ url: 'http://js.passport.qihucdn.com/5.0.2.js',type: 'GET',dataType: 'HTML',complete: function(){ console.log('complete:' + j++); } });
}