ajax大全
一、ajax介绍
用户通过浏览器向浏览器提交数据:
1、 通过form表单发送 (页面需要刷新)
2、 通过Ajax发送 (页面无刷新)
Ajax Asynchronous Javascript and XML (异步的Javascript和XML现在都不这样用了现在用json)一种创建交互式网页应用的网页开发技术方案;现在都用Asynchronous Javascript and JSON
通过在后台与服务器进行少量数据交换,AJAX 可以使网页实现异步更新。这意味着可以在不重新加载整个网页的情况下,对网页的某部分进行更新。传统的网页(不使用 AJAX)如果需要更新内容,必须重载整个网页页面。
二、iframe伪造Ajax
“伪”Ajax
由于HTML标签的frame标签具有局部加载内容的特性,所以可以使用其来伪造Ajax请求
通过iframe的src可以跳转到任何网站的特性来伪造局部加载Ajax
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title></title> <style> input.aa{ cursor: pointer; } </style> </head> <body> <div> <p>请输入要加载的地址:<span id="currentTime"></span></p> <p> <input id="url" type="text"/> <input class="aa" type="button" value="刷新" onclick="LoadPage();"/> </p> </div> <div> <h3>加载页面的位置:</h3> <iframe id="iframePosition" style="width: 100%;height: 500px;"></iframe> </div> <script type="text/javascript"> //页面全部加载之后自动执行后面的函数 window.onload= function () { var myDate=new Date(); document.getElementById("currentTime").innerText=myDate.getTime() }; function LoadPage(){ //用户输入什么然后触发iframe的src功能 var targetUrl=document.getElementById("url").value; document.getElementById("iframePosition").src=targetUrl; } </script> </body> </html>
三、原生Ajax
Ajax主要就是使用XMLHttpRequest对象来完成请求的操作,该对象在主流浏览器中均存在(除了早期的IE),Ajax首次出现在IE5.5中存在(Active控件)
1、XmlHttpRequest对象介绍
a. void open(String method,String url,Boolen async) 用于创建请求 参数: method: 请求方式(字符串类型),如:POST、GET、DELETE... url: 要请求的地址(字符串类型) async: 是否异步(布尔类型) b. void send(String body) 用于发送请求 参数: body: 要发送的数据(字符串类型) c. void setRequestHeader(String header,String value) 用于设置请求头 参数: header: 请求头的key(字符串类型) vlaue: 请求头的value(字符串类型) d. String getAllResponseHeaders() 获取所有响应头 返回值: 响应头数据(字符串类型) e. String getResponseHeader(String header) 获取响应头中指定header的值 参数: header: 响应头的key(字符串类型) 返回值: 响应头中指定的header对应的值 f. void abort() 终止请求
a. Number readyState 状态值(整数) 详细: 0-未初始化,尚未调用open()方法; 1-启动,调用了open()方法,未调用send()方法; 2-发送,已经调用了send()方法,未接收到响应; 3-接收,已经接收到部分响应数据; 4-完成,已经接收到全部响应数据; b. Function onreadystatechange 当readyState的值改变时自动触发执行其对应的函数(回调函数) c. String responseText 服务器返回的数据(字符串类型) d. XmlDocument responseXML 服务器返回的数据(Xml对象) e. Number states 状态码(整数),如:200、404... f. String statesText 状态文本(字符串),如:OK、NotFound...
2、跨浏览器支持
- XmlHttpRequest
IE7+, Firefox, Chrome, Opera, etc. - ActiveXObject("Microsoft.XMLHTTP")
IE6, IE5
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <title></title> </head> <body> <h1>XMLHttpRequest - Ajax请求</h1> <input type="button" onclick="XhrGetRequest();" value="Get发送请求" /> <input type="button" onclick="XhrPostRequest();" value="Post发送请求" /> <script src="/statics/jquery.js"></script> <script type="text/javascript"> function GetXHR(){ var xhr = null; if(XMLHttpRequest){ xhr = new XMLHttpRequest(); }else{ xhr = new ActiveXObject("Microsoft.XMLHTTP"); } return xhr; } function XhrPostRequest(){ var xhr = GetXHR(); // 定义回调函数 xhr.onreadystatechange = function(){ if(xhr.readyState == 4){ // 已经接收到全部响应数据,执行以下操作 var data = xhr.responseText; console.log(data); } }; // 指定连接方式和地址----文件方式 xhr.open('POST', "/s1", true); // 设置请求头 xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded; charset-UTF-8'); // 发送请求 xhr.send('n1=1;n2=2;'); } function XhrGetRequest(){ var xhr = GetXHR(); // 定义回调函数 xhr.onreadystatechange = function(){ if(xhr.readyState == 4){ // 已经接收到全部响应数据,执行以下操作 var data = xhr.responseText; console.log(data); } }; // 指定连接方式和地址----文件方式 xhr.open('get', "/s1", true); // 发送请求 xhr.send(); } </script> </body> </html>
#/usr/bin/env python #-*- coding:utf-8-*- import tornado.ioloop import tornado.web class IndexHandler(tornado.web.RequestHandler): def get(self, *args, **kwargs): self.render("s1.html") settings={ "template_path":"views", "static_path":"statics", "static_url_prefix":"/statics/" } application = tornado.web.Application([ (r"/s1",IndexHandler), ],**settings) if __name__=="__main__": application.listen(7777) tornado.ioloop.IOLoop.instance().start()
四、jquery发送Ajax请求
jQuery 既然是JavaScript的类库,那肯定也封装了AJAX使用相关方法,会使我们开发用起来更简单。
jQuery Ajax的本质无疑是 XMLHttpRequest 或 ActiveXObject
注:2.+的版本不再支持IE9以下的浏览器
jQuery Ajax 常用方法有三个:get、post、ajax:
# jQuery Ajax 常用方法列表 jQuery.get(...) 所有参数: url: 待载入页面的URL地址 data: 待发送 Key/value 参数。 success: 载入成功时回调函数。 dataType: 返回内容格式,xml, json, script, text, html jQuery.post(...) 所有参数: url: 待载入页面的URL地址 data: 待发送 Key/value 参数 success: 载入成功时回调函数 dataType: 返回内容格式,xml, json, script, text, html jQuery.ajax(...) 部分参数: url:请求地址 type:请求方式,GET、POST(1.9.0之后用method) headers:请求头 data:要发送的数据 contentType:即将发送信息至服务器的内容编码类型(默认: "application/x-www-form-urlencoded; charset=UTF-8") async:是否异步 timeout:设置请求超时时间(毫秒) beforeSend:发送请求前执行的函数(全局) complete:完成之后执行的回调函数(全局) success:成功之后执行的回调函数(全局) error:失败之后执行的回调函数(全局) accepts:通过请求头发送给服务器,告诉服务器当前客户端课接受的数据类型 dataType:将服务器端返回的数据转换成指定类型 "xml": 将服务器端返回的内容转换成xml格式 "text": 将服务器端返回的内容转换成普通文本格式 "html": 将服务器端返回的内容转换成普通文本格式,在插入DOM时,如果包含js标签,会尝试去执行 "script": 尝试将返回值当作JavaScript去执行,然后再将服务器端返回的内容转换成普通文本格式 "json": 将服务器端返回的内容转换成相应的JavaScript对象 "jsonp": JSONP 格式 使用 JSONP 形式调用函数时,如 "myurl?callback=?" jQuery 将自动替换 ? 为正确的函数名,以执行回调函数,如果不指定,jQuery 将自动根据HTTP包MIME信息返回相应类型(an XML MIME type will yield XML, in 1.4 JSON will yield a JavaScript object, in 1.4 script will execute the script, and anything else will be returned as a string converters: 转换器,将服务器端的内容根据指定的dataType转换类型,并传值给success回调函数
# jQuery Ajax 方法列表 jQuery.get(...) 所有参数: url: 待载入页面的URL地址 data: 待发送 Key/value 参数。 success: 载入成功时回调函数。 dataType: 返回内容格式,xml, json, script, text, html jQuery.post(...) 所有参数: url: 待载入页面的URL地址 data: 待发送 Key/value 参数 success: 载入成功时回调函数 dataType: 返回内容格式,xml, json, script, text, html jQuery.getJSON(...) 所有参数: url: 待载入页面的URL地址 data: 待发送 Key/value 参数。 success: 载入成功时回调函数。 jQuery.getScript(...) 所有参数: url: 待载入页面的URL地址 data: 待发送 Key/value 参数。 success: 载入成功时回调函数。 jQuery.ajax(...) 部分参数: url:请求地址 type:请求方式,GET、POST(1.9.0之后用method) headers:请求头 data:要发送的数据 contentType:即将发送信息至服务器的内容编码类型(默认: "application/x-www-form-urlencoded; charset=UTF-8") async:是否异步 timeout:设置请求超时时间(毫秒) beforeSend:发送请求前执行的函数(全局) complete:完成之后执行的回调函数(全局) success:成功之后执行的回调函数(全局) error:失败之后执行的回调函数(全局) accepts:通过请求头发送给服务器,告诉服务器当前客户端课接受的数据类型 dataType:将服务器端返回的数据转换成指定类型 "xml": 将服务器端返回的内容转换成xml格式 "text": 将服务器端返回的内容转换成普通文本格式 "html": 将服务器端返回的内容转换成普通文本格式,在插入DOM中时,如果包含JavaScript标签,则会尝试去执行。 "script": 尝试将返回值当作JavaScript去执行,然后再将服务器端返回的内容转换成普通文本格式 "json": 将服务器端返回的内容转换成相应的JavaScript对象 "jsonp": JSONP 格式 使用 JSONP 形式调用函数时,如 "myurl?callback=?" jQuery 将自动替换 ? 为正确的函数名,以执行回调函数 如果不指定,jQuery 将自动根据HTTP包MIME信息返回相应类型(an XML MIME type will yield XML, in 1.4 JSON will yield a JavaScript object, in 1.4 script will execute the script, and anything else will be returned as a string converters: 转换器,将服务器端的内容根据指定的dataType转换类型,并传值给success回调函数 $.ajax({ accepts: { mycustomtype: 'application/x-some-custom-type' }, // Expect a `mycustomtype` back from server dataType: 'mycustomtype', // Instructions for how to deserialize a `mycustomtype` converters: { 'text mycustomtype': function(result) { // Do Stuff return newresult; } }, });
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <title></title> </head> <body> <p> <input type="button" onclick="XmlSendRequest();" value='Ajax请求' /> </p> <script type="text/javascript" src="jquery-1.12.4.js"></script> <script> function JqSendRequest(){ $.ajax({ url: "http://c2.com:8000/test/", type: 'GET', dataType: 'text', success: function(data, statusText, xmlHttpRequest){ console.log(data); } }) } </script> </body> </html>
1、 导入jquery 2、 导入$.get({ url:”地址”, data:{“k1”:”v1”,...}, dataType:”script”,-->这里面可以有text,json,xml,script,jsonp.即这里是什么,那么da就默认是什么 success:function(da){ } }) $.getJson() $.getScript() 这两个方法就是上面缩写(内部会调用get方法),也就是把url,data,函数放到这里面,然后dataType()里面填写类型 3、 或者导入$.post({ url:”地址”, data:{“k1”:”v1”,...}, dataType:”script”,-->这里面可以有text,json,xml,script,jsonp.即这里是什么,那么da就默认是什么 success:function(da){ } )
五、文件上传
一、文件上传之form
下面上传文件,并且把这个文件单独分到一个文件包里面,并且让让这个文件展示在前台上面,这个上传必须是文件
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title></title> 1、这里注意,在input中的checkbox中,必须要有value才可以,这样提交到 后台,才会分得清到底用户点击了谁 2、要上传文件在form表单中必须定义enctype="multipart/form-data" 3、把上传的文件展示在前台页面上,可以自定义一个空列表。然后把上传的文件名传入 并且结合模板语言,把内容传入到这个列表中并且展示在页面 </head> <body> <ul> {% for item in img_list %} <li><img style="height: 100px;width: 100px" src="/statics/img/{{item}}"></li> {% end %} </ul> <form action="index" method="post" enctype="multipart/form-data"> <input type="text" name="user"/> <h3>爱好</h3> <input name="favor" type="checkbox" value="1"/>篮球; <input name="favor" type="checkbox" value="2"/>足球; <input name="favor" type="checkbox" value="3"/>玻璃球; 定义上传文件 <input type="file" name="fafafa"/> <input type="submit" value="提交"/> </form> </body> </html>
1 #/usr/bin/env python 2 #-*- coding:utf-8-*- 3 import tornado.ioloop 4 import tornado.web 5 6 IMG_LIST=[] 7 class IndexHandler(tornado.web.RequestHandler): 8 def get(self, *args, **kwargs): 9 #给用户返回前端页面和这个列表,并且在前台把这个列表填充内容 10 self.render("index.html" ,img_list=IMG_LIST) 11 def post(self, *args, **kwargs): 12 # print(self.get_argument("user")) 13 # print(self.get_argument("favor")) 14 # print(self.get_argument("fafafa")) 15 16 #获取文件名字 17 file_metas = self.request.files["fafafa"] 18 # print(file_metas) 下面是获取内容 19 for meta in file_metas: 20 #要上传的文件名 21 file_name = meta['filename'] 22 #把文件上传到后台的目录中 23 import os 24 with open(os.path.join("statics","img",file_name),'wb') as up: 25 up.write(meta['body']) 26 #把上传的文件名传入到这个列表中 27 IMG_LIST.append(file_name) 28 29 self.render("1") 30 31 settings={ 32 "template_path":"views", 33 "static_path":"statics", 34 "static_url_prefix":"/statics/" 35 } 36 application = tornado.web.Application([ 37 (r"/index",IndexHandler), 38 ],**settings) 39 if __name__=="__main__": 40 application.listen(7777) 41 tornado.ioloop.IOLoop.instance().start() 42 43 44 45 46 最主要是下面的方法: 47 def post(self, *args, **kwargs): 48 file_metas = self.request.files["fff"] 49 # print(file_metas) 50 for meta in file_metas: 51 file_name = meta['filename'] 52 with open(file_name,'wb') as up: 53 up.write(meta['body'])
二、文件上传之Ajax
基于原生Ajax上传代码
1 <!DOCTYPE html> 2 <html> 3 <head lang="en"> 4 <meta charset="UTF-8"> 5 <title></title> 6 </head> 7 <body> 8 <input type="file" id="img" /> 9 <input type="button" onclick="UploadFile();" /> 10 <script> 11 function UploadFile(){ 12 //获取文件对象 13 var fileObj = document.getElementById("img").files[0]; 14 //创建form对象 15 var form = new FormData(); 16 form.append("user", "v1"); 17 form.append("favor","1"); 18 form.append("fafafa", fileObj); 19 20 var xhr = new XMLHttpRequest(); 21 xhr.open("post", '/index', true); 22 xhr.send(form); 23 } 24 </script> 25 </body> 26 </html>
1 #/usr/bin/env python 2 #-*- coding:utf-8-*- 3 import tornado.ioloop 4 import tornado.web 5 6 IMG_LIST=[] 7 class IndexHandler(tornado.web.RequestHandler): 8 def get(self, *args, **kwargs): 9 #给用户返回前端页面和这个列表,并且在前台把这个列表填充内容 10 self.render("index.html" ,user_list=IMG_LIST) 11 def post(self, *args, **kwargs): 12 print(self.get_argument("user")) 13 print(self.get_argument("favor")) 14 # print(self.get_argument("fafafa")) 15 16 #获取文件名字 17 file_metas = self.request.files["fafafa"] 18 # print(file_metas) 下面是获取内容 19 for meta in file_metas: 20 #要上传的文件名 21 file_name = meta['filename'] 22 #把文件上传到后台的目录中 23 import os 24 with open(os.path.join("statics","img",file_name),'wb') as up: 25 up.write(meta['body']) 26 #把上传的文件名传入到这个列表中 27 IMG_LIST.append(file_name) 28 29 self.render("index.html") 30 31 settings={ 32 "template_path":"views", 33 "static_path":"statics", 34 "static_url_prefix":"/statics/" 35 } 36 application = tornado.web.Application([ 37 (r"/index",IndexHandler), 38 ],**settings) 39 if __name__=="__main__": 40 application.listen(7777) 41 tornado.ioloop.IOLoop.instance().start()
三、基于jQuery和Ajax上传文件
<!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8"> <title></title> </head> <body> <input type="file" id="img" /> <input type="button" onclick="UploadFile();" /> <script src="/statics/jquery.js"></script> <script> function UploadFile(){ var fileObj = $("#img")[0].files[0]; var form = new FormData(); form.append("user", "v1"); form.append("favor", "v1"); form.append("fafafa", fileObj); $.ajax({ type:'POST', url: '/index', data: form, processData: false, // tell jQuery not to process the data contentType: false, // tell jQuery not to set contentType success: function(arg){ console.log(arg); } }) } </script> </body> </html>
四、上传文件之Iframe
如果遇到浏览器不支持原生ajax或者jquery +ajax的形式上传文件,这个时候就可以选择用iframe来上传文件
这种形式的兼容性会更好一点,因为所有的浏览器都有iframe这个标签,利用iframe作为一个通道来来上传
1 <!DOCTYPE html> 2 <html> 3 <head lang="en"> 4 <meta charset="UTF-8"> 5 <title></title> 6 <style> 7 .hide{ 8 display: none; 9 } 10 </style> 11 </head> 12 <body> 13 <form id="my_form" name="form" action="/index" method="POST" enctype="multipart/form-data" > 14 <div id="main"> 15 <input name="user" type="text" /> 16 <input name="favor" type="text" /> 17 <input name="fafafa" id="my_file" type="file" /> 18 <input type="button" name="action" value="Upload" onclick="redirect()"/> 19 <iframe id='my_iframe' name='my_iframe' src="" class="hide"></iframe> 20 </div> 21 </form> 22 <script src="/statics/jquery.js"></script> 23 <script> 24 function redirect(){ 25 document.getElementById('my_iframe').onload = Testt; 26 //my_form这个标签的目标提交到my_iframe,然后iframe加载完成之后执行上面的方法 27 document.getElementById('my_form').target = 'my_iframe'; 28 document.getElementById('my_form').submit(); 29 30 } 31 32 function Testt(ths){ 33 //把iframe的内容提交给t 34 var t = $("#my_iframe").contents().find("body").text(); 35 console.log(t); 36 } 37 </script> 38 </body> 39 </html>
六、跨域ajax
1、对于Ajax请求,如果跨域名请求,默认【浏览器】不允许
出错地方在于:
在本地的ajax请求自己的域名是可以进行的,但是本地的Ajax请求的不是自己的域名,而是其他的域名,那么别的服务器也会进行处理和返回请求,但是浏览器接收的过程中出错了。浏览器的同源策略导致的 所以默认的ajax跨域请求是不能够完成的
2、允许跨域的有:
<script块 src=http://xxx.com/>
<img src=http://js.com/>
<iframe src=””/>
不允许跨域:
ajax
3、突破上面的限制:
和别的网站交互的时候用的。也就是合作的时候
两个办法:
办法一:JSONP,特别机智的方式 原理,动态创建script块,并且添加前台上面去
办法二:cors
JSONP(JSONP - JSON with Padding是JSON的一种“使用模式”),利用script标签的src属性(浏览器允许script标签跨域) 在客户端需要协商一个函数 function xx(args){ } 加上标签<script src=”xxx”> <script> xx({“status”:1,”message”:”sasd”},) </script> 服务器端: {“status”:1,”message”:”sasd”} 返回给用户:xx({“status”:1,”message”:”sasd”},)
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title></title> </head> <body> <input type="button" value="Ajax" onclick="DoAjax();"/> <input type="button" value="jsonPAjax" onclick="JsonPAjax();"/> <script src="/statics/jquery.js"></script> <script src="http://pyrene.com:8002/statics/jquery.cookie.js"></script> <script> function DoAjax(){ $.ajax({ url:"http://pyrene.com:8002/index", type:"POST", //定义对象必须为key/value格式 data:{"k1":"v1"}, //下面arg是返回的参数 success:function(arg){ console.log(arg); } }) } function JsonPAjax(){ // document.createElement("script"); // tag.src="http://pyrene.com:8002/index"; // document.head.appendChild(tag); // document.head.removeChild(tag) //下面是另一种方法,首先跨域访问,之后把访问的函数放到<script>标签内执行 $.ajax({ url:"http://pyrene.com:8002/index", dataType:"jsonp", jsonpCallBack:"func" }) } </script> </body> </html>
首先要去drivers里面修改hosts
在客户端需要一个函数func,然后访问另一个B服务器端,,B服务器端返回这个函数给这个A服务器的客户端的script标签内,然后通过渲染执行
#/usr/bin/env python import tornado.ioloop import tornado.web class IndexHnadler(tornado.web.RequestHandler): def get(self, *args, **kwargs): self.render("index.html") def post(self, *args, **kwargs): self.write("t3.post") settings={ "template_path":"views", "static_path":"statics", "static_url_prefix":"/statics/" } application=tornado.web.Application([ (r"/index",IndexHnadler), ],**settings) if __name__=="__main__": application.listen(1111) tornado.ioloop.IOLoop.instance().start()
#/usr/bin/env python import tornado.ioloop import tornado.web class IndexHnadler(tornado.web.RequestHandler): def get(self, *args, **kwargs): self.render("index.html") def post(self, *args, **kwargs): self.write("t3.post") settings={ "template_path":"views", "static_path":"statics", "static_url_prefix":"/statics/" } application=tornado.web.Application([ (r"/index",IndexHnadler), ],**settings) if __name__=="__main__": application.listen(1111) tornado.ioloop.IOLoop.instance().start()
基于jsonP实现跨域ajax示例之江西卫视节目表
更正式的需要在服务器后台加上下面的两行,即获取客户端用户输入的callback然后在前端代码中获取用户传入的callback和自定义函数,
#/usr/bin/env python import tornado.ioloop import tornado.web class IndexHnadler(tornado.web.RequestHandler): def get(self, *args, **kwargs): #获取用户传入的callback 这个是需要自定义的 callback=self.get_argument("callback") self.write("%s([11,22,33]);"%callback) def post(self, *args, **kwargs): self.write("t4.post") settings={ "template_path":"views", "static_path":"statics", "static_url_prefix":"/statics/" } application=tornado.web.Application([ (r"/index",IndexHnadler), ],**settings) if __name__=="__main__": application.listen(8002) tornado.ioloop.IOLoop.instance().start()
下面是调用江西卫视节目单的,前端代码和后台代码
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title></title> </head> <body> <input type="button" value="Ajax" onclick="DoAjax();"/> <input type="button" value="jsonPAjax" onclick="JsonPAjax();"/> <input type="button" value="jsonPJXAjax" onclick="JsonPJXAjax();"/> <script src="/statics/jquery.js"></script> <script src="http://pyrene.com:8002/statics/jquery.cookie.js"></script> <script> //定义函数 function uo(arg){ console.log(arg); } function DoAjax(){ $.ajax({ url:"http://pyrene.com:8002/index", type:"POST", //定义对象必须为key/value格式 data:{"k1":"v1"}, //下面arg是返回的参数 success:function(arg){ console.log(arg); } }) } function JsonPAjax(){ // document.createElement("script"); // tag.src="http://pyrene.com:8002/index"; // document.head.appendChild(tag); // document.head.removeChild(tag) //下面是另一种方法,首先跨域访问,之后把访问的函数放到<script>标签内执行 $.ajax({ url:"http://pyrene.com:8002/index", dataType:"jsonp", //下面这两句相当于在url后面加上?callback=uo jsonp:"callback", jsonpCallBack:"uo" }) } function list(dict){ console.log(dict); } function JsonPJXAjax(){ $.ajax({ url:"http://www.jxntv.cn/data/jmd-jxtv2.html?callback=list", dataType:"jsonp", jsonp:"callback", jsonpCallBack:"list" }) } </script> </body> </html>
#/usr/bin/env python import tornado.ioloop import tornado.web class IndexHnadler(tornado.web.RequestHandler): def get(self, *args, **kwargs): self.render("index.html") def post(self, *args, **kwargs): self.write("t3.post") settings={ "template_path":"views", "static_path":"statics", "static_url_prefix":"/statics/" } application=tornado.web.Application([ (r"/index",IndexHnadler), ],**settings) if __name__=="__main__": application.listen(1111) tornado.ioloop.IOLoop.instance().start()
如果要更加详细的调出节目单,那么直接在前台用一个for循环就可以了
基于cors实现跨域ajax 跨域资源共享
1 最新浏览器才支持cors功能的,jsonp是现在用的最多的一种 2 本质: 客户端不变,服务器端设置相应头即可 3 简单请求: 4 需要满足下面条件: 5 1、请求方式:HEAD、GET、POST 6 2、请求头信息: 7 Accept 8 Accept-Language 9 Content-Language 10 Last-Event-ID 11 Content-Type 对应的值是以下三个中的任意一个 12 application/x-www-form-urlencoded 13 multipart/form-data 14 text/plain 15 16 注意:同时满足以上两个条件时,则是简单请求,否则为复杂请求 17 18 简单请求和非简单请求的区别: 19 简单请求:一次请求。 20 非简单请求:两次请求,在发送数据之前会先发一次请求用作与“预检”,只有“预检”通过后才再发送一次请求用于数据传输 21 22 关于预检:预检都会执行OPTIONS方法 23 请求方式:OPTIONS 24 - “预检”其实做检查,检查如果通过则允许传输数据,检查不通过则不再发送真正想要发送的消息 25 - 如何“预检” 26 => 如果复杂请求是PUT等请求,则服务端需要设置允许某请求,否则“预检”不通过 27 Access-Control-Request-Method 28 => 如果复杂请求设置了请求头,则服务端需要设置允许某请求头,否则“预检”不通过 29 Access-Control-Request-Headers
下面就是图示
cors实现ajax跨域请求:
简单请求:需要设置响应头:Access-Control-Allow-Origin=”域名 或 *”
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title></title> </head> <body> <input type="button" value="Ajax" onclick="DoAjax();"/> <input type="button" value="DoAjaxComplex" onclick="DoAjaxComplex();"/> <script src="/statics/jquery.js"></script> <script> function DoAjax(){ $.ajax({ url:"http://pyrene.com:8002/cors", type:"POST", //定义对象必须为key/value格式 data:{"k1":"v1"}, //下面arg是返回的参数 success:function(arg){ console.log(arg); } }) }
class MainHandler(tornado.web.RequestHandler): def get(self): self.set_header('Access-Control-Allow-Origin', "http://www.xxx.com") self.write('{"status": true, "data": "seven"}')
支持复杂请求:
复杂请求主要是用options的方法,在options方法中设置如下:
由于复杂请求时,首先会发送“预检”请求,如果“预检”成功,则发送真实数据。
- “预检”请求时,允许请求方式则需服务器设置响应头:Access-Control-Request-Method
- “预检”请求时,允许请求头则需服务器设置响应头:Access-Control-Request-Headers
- “预检”缓存时间,服务器设置响应头:Access-Control-Max-Age
如果是put需要设置put方法来接收响应头等
注意在返回来的时候要设置允许网站回来
#/usr/bin/env python import tornado.ioloop import tornado.web class IndexHnadler(tornado.web.RequestHandler): def get(self, *args, **kwargs): callback=self.get_argument("callback") self.write("%s([11,22,33]);"%callback) def post(self, *args, **kwargs): self.write("t4.post") class CorsHandler(tornado.web.RequestHandler): def get(self, *args, **kwargs): self.write('{"status":1,"message":"get"}') def post(self, *args, **kwargs): self.set_header("Access-Control-Allow-Origin","*") self.write('{"status":1,"message":"post"}') def options(self, *args, **kwargs): print("options") #设置允许网站来,这里如果要设置cookie的话,那么下面的域名必须是指定的域名,不能是*了 # self.set_header("Access-Control-Allow-Origin","*") self.set_header("Access-Control-Allow-Origin","http://127.0.0.1:1111") #我允许put方法来,设置响应头 self.set_header("Access-Control-Allow-Methods","PUT,DELETE") #我允许请求头 self.set_header('Access-Control-Allow-Headers', "h1,h2") #设置允许带cookie,这个必须要放到预检上面 self.set_header("Access-Control-Allow-Credentials","true") #设置10秒钟只通过一次预检,如果超过10秒钟再来,那么还再一次进行预检 self.set_header('Access-Control-Max-Age', 10) #设置put方法接收 def put(self, *args, **kwargs): print(self.cookies) self.set_cookie("k1","aa") #设置允许网站回来,如果要携带cookie的时候这里的域名必须是具体的 # self.set_header("Access-Control-Allow-Origin","*") self.set_header("Access-Control-Allow-Origin","http://127.0.0.1:1111") #设置允许带cookie self.set_header("Access-Control-Allow-Credentials","true") self.write("ok") settings={ "template_path":"views", "static_path":"statics", "static_url_prefix":"/statics/" } application=tornado.web.Application([ (r"/index",IndexHnadler), (r"/cors",CorsHandler) ],**settings) if __name__=="__main__": application.listen(8002) tornado.ioloop.IOLoop.instance().start()
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title></title> </head> <body> <input type="button" value="Ajax" onclick="DoAjax();"/> <input type="button" value="DoAjaxComplex" onclick="DoAjaxComplex();"/> <script src="/statics/jquery.js"></script> <script> function DoAjax(){ $.ajax({ url:"http://pyrene.com:8002/cors", type:"POST", //定义对象必须为key/value格式 data:{"k1":"v1"}, //下面arg是返回的参数 success:function(arg){ console.log(arg); } }) } function DoAjaxComplex(){ $.ajax({ url:"http://pyrene.com:8002/cors", type:"PUT", //设置请求头 headers:{"h1":"hh"}, //定义对象必须为key/value格式 data:{"k1":"v1"}, //下面表示程序想要携带cookie xhrFields:{withCredentials: true}, //下面arg是返回的参数 success:function(arg){ console.log(arg); } }) } </script> </body> </html>
跨站传输cookie
在HTML中设置 //下面表示程序想要携带cookie xhrFields:{withCredentials: true},
在服务器后台中设置:这里注意把允许网站回来中的域名不能是*
即:服务器端响应的 Access-Control-Allow-Origin 不能是通配符 *
#设置允许带cookie,这个必须要放到预检上面 self.set_header("Access-Control-Allow-Credentials","true")
在put方法中,这里注意把允许网站回来中的域名不能是* #设置允许带cookie self.set_header("Access-Control-Allow-Credentials","true")