ajax跨域请求-jsonp
1. 同源策略
ajax之所以需要“跨域”,罪魁祸首就是浏览器的同源策略。即,一个页面的ajax只能获取这个页面相同源或者相同域的数据。
如何叫“同源”或者“同域”呢?——协议、域名、端口号都必须相同。例如:
http://google.com 和 https://google.com 不同,因为协议不同;
http://localhost:8080 和 http://localhost:1000 不同,因为端口不同;
http://localhost:8080 和 https://google.com 不同,协议、域名、端口号都不同,根本不是一家的。
根据同源策略,我自己做的一个网页 http://localhost:8080/test.html 就无法通过ajax直接获取 http://google.com 的数据。
例如,我用ajax去访问一个不同域的页面,错误结果是这样的:

大家想想,这样其实也有道理。如果没有同源策略,你我都可以随便通过ajax直接获取其他网站的信息,这还不乱套了。。。我自己做一个搜索界面,搜索时直接用ajax从百度获取数据,那不成了小偷了。。。
但是跨域访问是少不了的,mail.163.com 的网页可能需要从 news.163.com 域下获取新闻信息,那怎么办?——开始咱们的跨域之旅。(当然用iframe也可以实现)
2. 从“盗链”说起
互联网的许多网站之间图片相互盗链,A网站网页的img.src直接链接到B网站的图片地址,这是常有的事儿。说到“盗链”,大家第一想到的可能是如何去防止盗链,今儿咱不管那个。
你再想想“盗链”和“同源策略”这两个词之间有什么关系?——对,矛盾!既然都“同源策略”了,怎么还能“盗链”呢?
世间万物都有矛盾,有矛盾了照样可以和谐共处,并不一定非要你死我活。
重点:<img>的src(获取图片),<link>的href(获取css),<script>的src(获取javascript)这三个都不符合同源策略,它们可以跨域获取数据。因此,你可以直接从一些cdn上获取jQuery,并且你网站上的图片也随时可能被别人盗用,所有最好加上水印!
而我们今天的主角——jsonp——就是因为<script>的src不符合同源策略而来的。
3. JSONP
例如,域名 a.com 下有一个 a.com/test.html 网页,域名 b.com 下有一个 b.com/data.html 网页和 b.com/alert.js 文件。
引导第一步:简单引用js
编写 b.com/alert.js 如下:
alert(123);
对 a.com/test.html 编写如下代码:
<script type=‘text/javascript‘ src=‘http://b.com/alert.js‘/>
运行 a.com/test.html,结果很明显,就是弹出 【123】 。
引导第二步:引用js返回数据
将 b.com/alert.js 修改为:
myFn(100);
将 a.com/test.html 修改为:
<script>
function myFn ( data ) {
alert( data + ‘px‘ );
}
</script>
<script type=‘text/javascript‘ src=‘http://b.com/alert.js‘/>
运行 a.com/test.html,结果是弹出【 100px 】,这个应该也没有什么疑问。
引导第三步:已经跨域成功!
第二步中,如果data——即100——是我要跨域在b.com下获取的一个数据,那么咱们这不就是已经实现跨域请求了吗!!!
把这个过程再清晰的捋一遍:
- <script>的src不符合同源策略;
- 我通过给<script>的src赋值一个跨域的文件的网址(可能不是一个js文件),这个文件返回的字符串,浏览器会当作javascript来解析;
- 而这段javascript中,就可以包含着我所需要的跨域服务器端的数据;
- 最后,我在本页面定义一个myFn函数用来展示数据,而这段javascript中就可以直接调用myFn函数;
引导第四步:引用html格式
<script>的src不一定仅仅指向javascript文件,可以指向任何地址。例如:
将 a.com/test.html 修改为:
<script>
function myFn ( data ) {
alert( data + ‘px‘ );
}
</script>
<script type=‘text/javascript‘ src=‘http://b.com/data.html‘/>
将 b.com/data.html 编写为:(注意,data.html中就写以下一行代码,多了不写)
myFn(100);
运行 a.com/test.html ,结果依然是【 100px 】
其中,“100”就是我们要跨域请求的数据。
引导第五步:动态数据
如果要请求的数据是动态的,那就要在动态页面中编写。
那么我们就让 a.com/test.html 去调用一个动态的aspx页面:
<script>
function myFn ( data ) {
alert( data + ‘px‘ );
}
</script>
<script type=‘text/javascript‘ src=‘http://b.com/data.aspx?callback=myFn‘/>
大家注意,我们在 src 地址中增加了“?callback=myFn”,意思是把显示数据的函数也动态传过去了,而第二步、第四步都是静态的写在被调用的文件中的。
至于callback参数后台如何接收,如何使用,请接着看:
在 b.com 下增加一个 b.com/data.aspx 页面,后台代码如下:
protected void Page_Load(object sender, EventArgs e)
{
if (this.IsPostBack == false)
{
string callback = "";
if (Request["callback"] != null)
{
callback = Request["callback"]; //服务器端要返回的数据
string data = "1024"; Response.Write(callback + "(" + data + ")");
}
}
}
代码很简单,获取callback参数,然后组成一个函数的形式返回。如果“b.com/data.aspx?callback=myFn”调用的话,那么返回的就是" myFn(1024) "。
返回的数据变成动态的了(“1024”),前端页面用于显示数据的函数也编程了动态的了(“callback=myFn”),但是归根结底,形式还是一样的。
引导第六步:调用封装
a.com/test.html 中,仅仅有一个<script>静静的躺在那里,执行一次之后,就没有作用了。
而实际情况是,a.com/test.html 中,可能随着用户的操作发生若干次的调用。怎么办?——动态增加呗。
function addScriptTag(src) {
var script = document.createElement("script");
script.setAttribute("type", "text/javascript");
script.src = src;
document.body.appendChild(script);
}
function myFn (data) {
alert(data + ‘px‘);
}
//需要调用时:
//addScriptTag(‘b.com/data.aspx?callback=myFn‘);
4. 总结
以上层层描述的就是JSONP,你不必去记住它的定义,看明白了上述文字,就全能理解。
重点在于:同源策略 + <script>的src不属于同源策略 + 通过<script>的src指向的文件返回服务器端数据。
ok,就这些!
ajax跨域请求-jsonp的更多相关文章
- AJAX 跨域请求 - JSONP获取JSON数据
Asynchronous JavaScript and XML (Ajax ) 是驱动新一代 Web 站点(流行术语为 Web 2.0 站点)的关键技术.Ajax 允许在不干扰 Web 应用程序的显示 ...
- 【JS跨域请求】Ajax跨域请求JSONP
前两天被问到ajax跨域如何解决,还真被问住了,光知道有个什么jsonp,迷迷糊糊的没有说上来.抱着有问题必须解决的态度,我看了许多资料,原来如此... 为何一直知道jsonp,但一直迷迷糊糊的不明白 ...
- 【转】AJAX 跨域请求 - JSONP获取JSON数据
来源:http://justcoding.iteye.com/blog/1366102/ Asynchronous JavaScript and XML (Ajax ) 是驱动新一代 Web 站点(流 ...
- ajax跨域请求のJSONP
简单说了一下,JSON是一种基于文本的数据交换方式,或者叫做数据描述格式. JSON的优点: 1.基于纯文本,跨平台传递极其简单: 2.Javascript原生支持,后台语言几乎全部支持: 3.轻量级 ...
- ajax跨域请求--jsonp实例
ajax请求代码: //区域事件选择配送点 function changeDistrict(value){ if(value == 0){ $('#transport_node').empty(); ...
- jsonp其实很简单【ajax跨域请求】
js便签笔记(13)——jsonp其实很简单[ajax跨域请求] 前两天被问到ajax跨域如何解决,还真被问住了,光知道有个什么jsonp,迷迷糊糊的没有说上来.抱着有问题必须解决的态度,我看了许多资 ...
- JAVAEE——宜立方商城11:sso登录注册功能实现、通过token获得用户信息、Ajax跨域请求(jsonp)
1. 学习计划 第十一天: 1.sso注册功能实现 2.sso登录功能实现 3.通过token获得用户信息 4.Ajax跨域请求(jsonp) 2. Sso系统工程搭建 需要创建一个sso服务工程,可 ...
- 利用jsonp进行Ajax跨域请求
在进行Ajax请求的时候经常会遇到跨域的问题,这个时候一般就会用到jsonp. 关于json和jsonp,网上有很多原理解释,这里就不多赘述,需要的自行搜索. 下面是一个简单的ajax跨域请求示例: ...
- JSONP实现Ajax跨域请求
前言 由于浏览器存在同源策略的机制,所谓同源策略就是阻止从一个源(域名,包括同一个根域名下的不同二级域名)加载的文档或者脚本获取/或者设置另一个源加载的文档属性. 但比较特别的是:由于同源策略是浏览器 ...
随机推荐
- review32
一个类的两个对象如果具有相同的引用,那么他们就具有相同的实体和功能.
- jsp:<c:redirect> 和<c:param> 标签
redirect 标签使用来进行页面之间的重定向,它和传统 JSP 程序中的<jsp:redirect>标记功能相类似.param 标签是和 redirect 一起使用的,它用来进行参数值 ...
- 使用JMeter建立接口测试
[需求]某组机器是Android和iOS输入法接口服务器,有很多重要的接口,例如:升级,网络开关,热词等.现在有3台机器过保要下线,新申请了3台机器,需要验证一下这3台机器接口的正确性. [测试步骤] ...
- CodeForces - 799B-T-shirt buying (优先队列)
题目链接 /* Name: Copyright: Author: Date: 2018/5/2 16:09:54 Description:优先队列 */ #include <iostream&g ...
- sql-多表查询JOIN与分组GROUP BY
一.内部连接:两个表的关系是平等的,可以从两个表中获取数据.用ON表示连接条件 SELECT A.a,B.b FROM At AS A INNER JOINT Bt AS B ON A.m=B.n ...
- pthread_cond_wait() 前使用 while 讲解
pthread_cond_wait() 前使用 while 讲解 -- : LINUX环境下多线程编程肯定会遇到需要条件变量的情况,此时必然要使用pthread_cond_wait()函数.但这个函数 ...
- nodepad++的python环境变量设置
转:http://blog.csdn.net/memray/article/details/42041975
- xj监控端口,模拟登陆脚本
#!/bin/bash date=`date +%Y%m%d-%H%M` count=0 ip1=124.117.246.195 ip2=124.117.246.194 port1=(443 80 6 ...
- CEF源码编译
CEF的构造说明:https://bitbucket.org/chromiumembedded/cef/wiki/BranchesAndBuilding chromium的源码地址:https://c ...
- 反射ORM 三层(for sql server/mysql)
sql server and oracle 不同之处只在于: 1·参数@和: 2·自增和序列 RPROM.cs //(写错愕,应该是RPORM) RPROM.Insert(p1); //需求:DBS中 ...