前端技术发展至今,已有的通信方式大概有四种:ajax、JSONP、SSE、websocket。对于ajax已经非常熟悉,但是对于JSONP 仍然有很多不明白的地方,今天学习了一下,在这和大家分享。
根据书上说,JSONP 就是json with padding,但是,不是特别理解。JSONP 其实是和script标签有很大的关系,JSONP最大的优势就是实现异步跨域的作用,它到底是怎么做到的呢?其实JSONP就是利用script的src属性,实现跨域功能的。我们用一个例子来说明:
<script>
function processJSON(json){
console.log('do something with json response');
}
</script>
<script src="http://www.girls.hustonline.net?callback=processJSON&name=jimmy&age=10"></script>
上面的代码中src中的内容就是前端发送的JSONP 的内容,其中processJSON就是一个回调函数,使用callback来指定它,当我们把JSONP 发送出去后,后台服务器会返回给我们一个data,将data传给回调函数来处理,即callback指定的processJSON(data),来执行服务器返回的内容。实际中的JSONP 请求应该是异步添加script标签的,下面是动态添加script标签的模拟代码:
前端js代码:
var sendJSONP=function(url,callbackName){
var script=document.createElement("script");
script.src='$(url)&callback=$(callbackName)';
document.head.appendChild(script);
};
var sayName=function(name){
console.log('your name is ${name}');
};
sendJSONP('http://girls.hustonline.net?name=jimmy','sayName');
nodejs 实现的后端代码:
const util=require('util'),
http=require('http'),
url=require('url');
let data=JSON.stringify({
message:"I HAVE ALREADY RECEIVED"
});
http.createServer(function(req,res){
req=url.parse(req.url,true);
if(!req.query.callback) res.end();
console.log(name is ${req.query.name)}and his age is ${req.query.age}');
res.writeHead(200,{'Content-Type':'appliction/javascript'})
res.end(req.query.callback+"('"+data+"')")
}).listen(80)
这样就完成了一个简单的JSONP函数的执行。
除了这种原生的方式,我们还可以通过jquery的getJSON 和 $.ajax完成JSONP的跨域请求。如下:
$.getJSON("http://girls.hustonline.net?callback=?",
function(result){
console.log(result);
}
);
$.ajax({
url:"http://girls.hustonline.net?name=jimmy",
dataType:'jsonp',
success:function(name){
console.log(name);
}
})
通过以上代码,我们会发现,在getJSON 方法中,url里面的"callback=?“,其中 ”?“ 实际上是jquery 使用自动生成数的方式,省去了我们给回调函数命名的困扰,最后“?”会被一串字符串代替,比如json1234567.这个就代表你的回调函数名。由于这里的“?”,很容易被忘掉,所以我们还是推荐使用$.ajax的方式。
由上可见,利用jquery 可以很简单的发送jsonp,所以也是我们推荐的方式。