原生Javascript封装的一个AJAX函数分享


Posted in Javascript onOctober 11, 2014

最近的工作中涉及到大量的ajax操作,本来该后台做的事也要我来做了.而现在使用的ajax函数是一个后台人员封装的—-但他又是基于jquery的ajax,所以离开了jquery这个函数就毫无作用了.而且我觉得,jquery的ajax方法是很完善的了,可以直接用,如果都有jquery了,那么他的ajax就不用白不用了.我缺少的是一个能在没有jquery的情况下使用的ajax方法.

所以我也花一天时间写了一个,参数与调用方法类似于jquery的ajax.就叫xhr吧,因为xhr=XMLHttpRequest.

/*

* Name: xhr,AJAX封装函数

* Description: 一个ajax调用封装类,仿jquery的ajax调用方式

* Author:十年灯

*/

var xhr = function () {

    var 

    ajax = function  () {

        return ('XMLHttpRequest' in window) ? function  () {

                return new XMLHttpRequest();

            } : function  () {

            return new ActiveXObject("Microsoft.XMLHTTP");

        }

    }(),

    formatData= function (fd) {

        var res = '';

        for(var f in fd) {

            res += f+'='+fd[f]+'&';

        }

        return res.slice(0,-1);

    },

    AJAX = function(ops) {

        var     

        root = this,

        req = ajax();
        root.url = ops.url;

        root.type = ops.type || 'responseText';

        root.method = ops.method || 'GET';

        root.async = ops.async || true;     

        root.data = ops.data || {};

        root.complete = ops.complete || function  () {};

        root.success = ops.success || function(){};

        root.error =  ops.error || function (s) { alert(root.url+'->status:'+s+'error!')};

        root.abort = req.abort;

        root.setData = function  (data) {

            for(var d in data) {

                root.data[d] = data[d];

            }

        }

        root.send = function  () {

            var datastring = formatData(root.data),

            sendstring,get = false,

            async = root.async,

            complete = root.complete,

            method = root.method,

            type=root.type;

            if(method === 'GET') {

                root.url+='?'+datastring;

                get = true;

            }

            req.open(method,root.url,async);

            if(!get) {

                req.setRequestHeader("Content-type","application/x-www-form-urlencoded");

                sendstring = datastring;

            }      
            //在send之前重置onreadystatechange方法,否则会出现新的同步请求会执行两次成功回调(chrome等在同步请求时也会执行onreadystatechange)

            req.onreadystatechange = async ? function  () {

                // console.log('async true');

                if (req.readyState ==4){

                    complete();

                    if(req.status == 200) {

                        root.success(req[type]);

                    } else {

                        root.error(req.status);

                    }                   

                }

            } : null;

            req.send(sendstring);

            if(!async) {

                //console.log('async false');

                complete();

                root.success(req[type]);

            }

        }

        root.url && root.send();        

    };

    return function(ops) {return new AJAX(ops);}    

}();

参数说明:

1.url:请求地址.可以不填,请求就不会发起,但如果不填又强行send,出了错不怪我
2.method: ‘GET'或'POST',全大写,默认GET
3.data: 要附带发送的数据,格式是一个object
4.async: 是否异步,默认true
5.type: 返回的数据类型,只有responseText或responseXML,默认responseText
6.complete: 请求完成时执行的函数
7.success: 请求成功时执行的函数
8.error: 请求失败时执行的函数

注:其中的type参数,并没有jquery的dataType那么丰富,只有原生AJAX有的responseText或responseXML.要是返回的是json数据,你需要在success函数中自己处理一下把text转成json.

函数说明:

一个实例化的xhr对象有两个函数可使用,一个是send,调用方法是:xhr.send(),无参数,其作用是发起请求过程.如果初始化时没有url,则不会执行send方法,这样你就可以在后面再加入url,并手动发起send—-如果send的时候没有url,那么请求会失败并且我没有处理这个错误,出了错只有你自己找了.

另一个方法是setData,调用方法是xhr.setData(data_obj),其参数是一个object. setData方法的作用是局部替换xhr的data属性里的值,比如xhr.data中已有一个page:1,你可以用xhr.setData({page:2})来更新他的值,而不影响data中已存在的其他属性值.

调用方法:

var a1 = xhr({

        url:'2.php',

        data:{

            'username':'lix',

            'password':'123456',

            'gender':'male',

            'interset':'play'

        },

        async:false,

        method:'GET',

        success: function  (data) {

            var obj = JSON.parse(data);

            //....

        }

    });

注:不用写new

特色介绍:

经过这段时间的项目经验,我发现一个ajax类应该具有一个很常见的特色:便于重复发起请求.比如项目中我写分页ajax的时候,每次翻页都要发送请求,但发送的数据中除了当前页码和每页条数,其他的都是不会改变的.如果多次这样的请求,都要重复定义那些不变的参数,无疑是种资源浪费.

所以这个xhr函数,就已经考虑了这个功能.还是拿分页的例子来说,我们可以在页面加载完成的时候就初始化一个xhr对象,保存为变量a1,当发起翻页请求时,其他的什么参数都没变,但pageNumber变了,此时就可以调用xhr的setData方法,把pageNumber改掉.

a1.setData({pageNumber:2});

注:setData的参数也是一个object.

当然,你也可以把data全盘替换:

a1.data = {…};

不只是data,你可以对a1这个已经实例化的xhr对象进行更多的更改,比如换掉url,换掉success函数,GET换成POST,同步换成异步…换完之后,再调用a1.send()方法,他就会按你的设置再次发起请求了.

当然,如果是完全不相关的另一个ajax请求,就没有必要硬要用这个现成的a1了.我们可以再实例化一个xhr,叫a2什么的.

如果你对xhr这个名字不满意,那就只有自己改掉了.

另外提供压缩加密版.未压缩版去掉注释大概2kb,压缩版1.00kb.

var xhr=function(){var e=function(){return"XMLHttpRequest"in window?function(){return new XMLHttpRequest}:function(){return new ActiveXObject("Microsoft.XMLHTTP")}}(),t=function(e){var t="";for(var n in e){t+=n+"="+e[n]+"&"}return t.slice(0,-1)},n=function(n){var r=this,i=e();r.url=n.url;r.type=n.type||"responseText";r.method=n.method||"GET";r.async=n.async||true;r.data=n.data||{};r.complete=n.complete||function(){};r.success=n.success||function(){};r.error=n.error||function(e){alert(r.url+"->status:"+e+"error!")};r.abort=i.abort;r.setData=function(e){for(var t in e){r.data[t]=e[t]}};r.send=function(){var e=t(r.data),n,s=false,o=r.async,u=r.complete,a=r.method,f=r.type;if(a==="GET"){r.url+="?"+e;s=true}i.open(a,r.url,o);if(!s){i.setRequestHeader("Content-type","application/x-www-form-urlencoded");n=e}i.onreadystatechange=o?function(){if(i.readyState==4){u();if(i.status==200){r.success(i[f])}else{r.error(i.status)}}}:null;i.send(n);if(!o){u();r.success(i[f])}};r.url&&r.send()};return function(e){return new n(e)}}()

xhr肯定有不完善的地方,以后使用中如果发现了,我会及时修正的.如果你用得不爽或发现不足,也请不吝提出改进意见.

Javascript 相关文章推荐
最新28个很棒的jQuery 教程
May 28 Javascript
如何使用JS获取IE上传文件路径(IE7,8)
Jul 08 Javascript
JavaScript也谈内存优化
Jun 06 Javascript
JS表格组件神器bootstrap table详解(基础版)
Dec 08 Javascript
Node.js操作Firebird数据库教程
Mar 04 Javascript
微信小程序本作用域下调用全局JS详解及实例
Feb 22 Javascript
Angular4学习笔记之根模块与Ng模块
Sep 09 Javascript
vue 全选与反选的实现方法(无Bug 新手看过来)
Feb 09 Javascript
去掉vue 中的代码规范检测两种方法(Eslint验证)
Mar 21 Javascript
Vue中div contenteditable 的光标定位方法
Aug 25 Javascript
Node 搭建一个静态资源服务器的实现
May 20 Javascript
ES6学习笔记之let与const用法实例分析
Jan 22 Javascript
探讨js字符串数组拼接的性能问题
Oct 11 #Javascript
分享20款美化网站的 jQuery Lightbox 灯箱插件
Oct 10 #Javascript
Jquery $.getJSON 在IE下的缓存问题解决方法
Oct 10 #Javascript
js点击button按钮跳转到另一个新页面
Oct 10 #Javascript
jQuery获取iframe的document对象的方法
Oct 10 #Javascript
jquery实现多行文字图片滚动效果示例代码
Oct 10 #Javascript
一个js过滤空格的小函数
Oct 10 #Javascript
You might like
PHP通用检测函数集合
2011/02/08 PHP
php中通过curl smtp发送邮件
2012/06/05 PHP
PHP限制页面只能在微信自带浏览器访问的代码
2014/01/15 PHP
javascript之函数直接量(function(){})()
2007/06/29 Javascript
定义select的边框颜色
2008/04/28 Javascript
学习ExtJS(一) 之基础前提
2009/10/07 Javascript
Javascript 复制数组实现代码
2009/11/26 Javascript
jQuery 跨域访问问题解决方法
2009/12/02 Javascript
jQuery生成asp.net服务器控件的代码
2010/02/04 Javascript
IE JS无提示关闭窗口不提示的方法
2010/04/29 Javascript
Javascript 设计模式(二) 闭包
2010/05/26 Javascript
node.js入门教程迷你书、node.js入门web应用开发完全示例
2014/04/06 Javascript
JavaScript中反正弦函数Math.asin()的使用简介
2015/06/14 Javascript
JQuery实现简单的服务器轮询效果实例
2016/03/31 Javascript
整理关于Bootstrap表单的慕课笔记
2017/03/29 Javascript
微信小程序组件之srcoll-view的详解
2017/10/19 Javascript
使用Angular CLI进行单元测试和E2E测试的方法
2018/03/24 Javascript
详解基于Node.js的HTTP/2 Server实践
2018/05/31 Javascript
Vue实现购物车详情页面的方法
2019/08/20 Javascript
JavaScript中跨域问题的深入理解
2021/03/04 Javascript
[01:02:48]2018DOTA2亚洲邀请赛 4.1 小组赛 A组 LGD vs OG
2018/04/02 DOTA
[01:31:22]DOTA2-DPC中国联赛定级赛 LBZS vs Magma BO3第二场 1月10日
2021/03/11 DOTA
Python Json序列化与反序列化的示例
2018/01/31 Python
Python numpy 点数组去重的实例
2018/04/18 Python
Python3中正则模块re.compile、re.match及re.search函数用法详解
2018/06/11 Python
详解如何在Apache中运行Python WSGI应用
2019/01/02 Python
浅析Python数字类型和字符串类型的内置方法
2019/12/22 Python
python 使用elasticsearch 实现翻页的三种方式
2020/07/31 Python
CSS3实现全景图特效示例代码
2018/03/26 HTML / CSS
瑞典最好的运动鞋专卖店:Sneakersnstuff
2016/08/29 全球购物
Clarks英国官方网站:全球领军鞋履品牌
2016/11/26 全球购物
SKECHERS官方旗舰店:美国舒适运动休闲品牌
2017/12/22 全球购物
Ellos瑞典官网:北欧地区时尚、美容和住宅领域领先的电子商务网站
2019/11/21 全球购物
大学生未来职业生涯规划书
2014/02/15 职场文书
财产分割协议书
2016/03/22 职场文书
Vue h函数的使用详解
2022/02/18 Vue.js