Ajax:Asynchronous JavaScript and XML(异步js和XML)javascript
//XML的格式类型; <name>大力丸</name> <age>18</age> <qq>714206204</qq> <email>daliwan@126.com</email>
js与后端进行数据交互的一种技术,经过请求协商好的接口,来获取到想要的数据php
传输数据时候会在本页面请求服务器,不用跳转页面,从而减轻服务器压力。作到实时验证,减小用户返工率而且优化用户体验java
var val=inputs[0].value; //下面这个是ajax对象; var ajax=new XMLHttpRequest;
//open是ajax对象上的一个方法; ajax.open("get","php/get.php?user="+val,true); //第一个参数决定是get仍是post方式; //第二个参数是请求地址,而且把要提交的加上去; //第三个参数true表明异步,false表明同步;
ajax.send();
ajax.onload=function(){ //响应好了就接受数据; span.innerHTML=ajax.responseText; }
ajax.responseText这是服务器返回的值:
1.确定是字符串,有的看起来是对象,实际上是json的形式;ajax
2.用JSON的方法:JSON.parse(aja.responseText)
转成真正的对象就能够用对象操做的方法去操做了;json
//写一个兼容性的函数,实现跨浏览器; var ajax=null; if(window.XMLHttpRequest){ ajax=new XMLHttpRequest; }else{ ajax=new ActiveXObject(Microsoft.XMLHTTP) };
get方式后端
拼接数据的时候要用encodeURI
转一下码,否则有中文就会乱码;跨域
> `encodeURI`把文字转成符号;
decodeURI
把符号转成文字;数组
post方式浏览器
ajax.setRequestHeader('Content-Type','application/x-www-form-urlencoded');
//建立对象; var ajax=null; if(window.XMLHttpRequest){ ajax=new XMLHttpRequest; }else{ ajax=new ActiveXObject(Microsoft.XMLHTTP) }; //填写请求地址; ajax.open("post","php/post.php",true); //发送请求,要在send前设置一下请求头; ajax.setRequestHeader('Content-Type','application/x-www-form-urlencoded'); ajax.send("user="+val) //下面的步骤和get方法是同样的;
一、当
send()
方法调用后会等待服务器返回信息,若是服务器一直没有响应,就会阻塞后面的代码,后面的代码就不会执行
二、后面的代码执行受前面代码的影响,前面的代码没跑通,后面的代码就不会执行缓存
一、当
send()
方法调用后,就会执行后面的代码,不用等待服务器的响应
二、后面的代码执行不受前面代码的影响
ajax.readState
ajax的运行步骤(第一步捕捉不到)
ajax.status
(状态码)
onreadStateChange
readstate
的值发生变化就会触发这个事件;
onload
全部请求成功完成后触发,此时的
readstata
的值为4
IE(6,7,8)不支持
如今这个方法逐渐取代onreadstatechange
这个方法了
ajax.onreadstatechange=function(){ if(ajax.readstate==4){ //服务区响应完成了; if(ajax.status==200){ //服务器正常; //这里放要执行的代码; } } }
封装ajax函数,传进函数里面的参数实际上是一个对象;
对象中包包含如下几种数据,包含在一个对象里面:
function ajax(json){ //默认参数; var settings={ url:"", method:"get", data:{}, dataType:"json", succ:null, fail:null } //用户传的参数覆盖默认参数; for (var attr in json){ settings[attr]=json[attr]; } //把data拼成正确的格式; var arr=[]; for (var attr in settings.data){ arr.push(attr+"="+settings.data[attr]); } settings.data=arr.join("&"); //声明变量; var ajax=window.XMLHttpRequest?new XMLHttpRequest():ActiveXObject("Microsoft.XMLHTTP"); //设置请求方式; //请求地址里面的new Date()方法,是为了设置不一样的时间戳去解决缓存的问题; if(settings.method.toLocalLowCase==="get"){ ajax.open("get",settings.url+"?"+settings.data+"&"+new Date().getTime(),true); ajax.send(); }else{ ajax.open("post",settings.url,true); //注意要设置一个请求头; ajax.setRequestHeader('Content-Type','application/x-www-form-urlencoded'); ajax.send(settings.data); } //设置完成时间的兼容性;IE6下是没有ajax.onload方法的; if(typeof ajax.onload==="undefined"){ ajax.onreadystatechange=ready; }else{ ajax.onload=ready; } //封装一个ready()函数; function ready(){ if(ajax.readystate==4){ if(ajax.status==200){ //用一个switch判断返回值得类型; switch(settings.dataType.toLocalLowCase()){ case "string" : settings.succ(ajax.responseText); break; case "json" : //把responsetext转成json格式; setting.succ(JSON.parse(ajax.responseText)); break; case "xml" : settings.succ(ajax.responseXml); break; } }else{ settings.fail(ajax.status); } } } }
要注意第57行的JSON.parse在低版本的浏览器中是不兼容的,须要下载一个json2.js的文件解决这个问题;
ajax.upload.onprogress 上传的进度事件;就是上传的时候要作的事情;
ev.loaded
已经上传的文件大小;ev.total
总的文件大小;经过这个能够作出来一个上传的进度条;
用H5中的<progress></progress>
这个API;
files 上传的选中的文件列表;
1.包括文件大小、类型、最后修改的时间等等;
**我本身对于FormData的理解:
FormDate能够new出来一个实例,这个实例能够继承它身上的append方法;这个操做放在ajax.open
和ajax.send
之间**
var formdata=new FormData(); //下面经过循环把选中的文件里面的额东西添加到这个对象身上; for(var i=0;i<inputs[0].files.length;i++){ //inputs[0]指的是一个type="file"的表单控件; formdata.append("file",inputs[0].files[i]); } //这时候formdata就能够被发送给服务器了,前面加上一个请求头;
两个不一样域名下的数据进行交互。Ajax之因此不能跨域实际上是由于XMLHttpRequest受到同源策略的限制,只能让它访问同源下的数据,不能访问不一样源下的数据;
每一个网站只能读取同一来源的数据,这里的同一来源指的是主机名(域名)、协议(http/https)和端口号的组合。在没明确受权的状况下,不能读写对方的资源,它是浏览器最核心也最基本的安全功能;
只要有一个不同就跨域;
解决跨域的方法:
这些方法都不是最优的,下面提供一种方法叫作 jsonp
jsonp的概念(json+padding)
带src属性的<script><img><iframe><link>等标签是不须要遵照同源策略的,可是经过src加载的资源,浏览器限制了javascript的权限,能读不能写;这就是jsonp能实现跨域的缘由;
jsonp中的回调函数
请求到的结果是这样的getData({"color":["red","green","blue"]})
注意callback是要设置成全局的,要不就放在操做的前面;
function jsonp(obj){ var settings={ url:'', //地址 data:{}, //要发送的数据 callBack:'callback', //url里存储回调函数名字的变量 fnName:'jsonp_'+new Date().getTime(), //回调函数的名字 succ:function(){} //请求成功的回调函数 }; for(var attr in obj){ settings[attr]=obj[attr]; } //建立一个script标签 var script=document.createElement("script"); script.className='sc'; settings.data[settings.callBack]=settings.fnName; var head=document.getElementsByTagName('head')[0]; //把要传的数据拼起来 var arr=[]; //['wd=sds','cb=jQuery1'] for(var attr in settings.data){ arr.push(attr+'='+settings.data[attr]); } settings.data=arr.join('&'); script.src=settings.url+'?'+settings.data; head.appendChild(script); //把回调函数挂载到window身上 window[settings.fnName]=function(data){ //当调用这个函数的时候,先把页面中全部的已经请求过的script删掉 var scripts=head.getElementsByTagName('script'); for(var i=0;i<scripts.length;i++){ if(scripts[i].className=='sc'){ head.removeChild(scripts[i]); } } settings.succ(data); }; }