json p全称为:json padding
形如:response.write(${query.callbackName}.call(undifined,'success')
)
或者是:callback({"name":"hax","gender":"Male"}
)
json p的实现步骤
请求方:rose.com的前端程序员(浏览器)
响应方:jack.com的后端程序员(服务器)
1.请求方创建script,src指向响应方,同时传一个查询参数?callbackName=yyy
2,响应方根据查询参数callbackName,构造形如
1,yyy.call(undefined,'你要的数据')
yyy('你要的数据')
2.浏览器接受到相应,就会执行yyy.call(undefined,'你要的数据')
3.那么请求方就知道了他要的数据,并且本站脚本可在callback函数里处理所传入的数据
json p的核心:动态添加<script>脚本来调用服务器提供的js脚本
jon p为什么不支持post
SONP的实现原理是在DOM中动态插入script脚本发送请求,服务器接收请求后返回数据。显然script不支持post,所以jsonp就不支持post
实现一个用jquery的json p形式
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>首页</title>
</head>
<body>
<h5>你的账户余额是<span id="amount">&&&amount&&&</span></h5>
<button id="button">打钱</button>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.min.js">
console.log(111)
</script>
<script>
button.addEventListener('click', (e)=>{
$.ajax({
url: "http://stu.com:8002/pay",
jsonp: "callback",
dataType: "jsonp",
success: function( response ) {
if(response==='success'){
amount.innerText=amount.innerText-1
}
}
})
})
// button.addEventListener('click', (e)=>{
// let script = document.createElement('script')
// let functionName = 'luostu'+ parseInt(Math.random()*10000000 ,10)
// window[functionName] = function(){ // 每次请求之前搞出一个随机的函数
// amount.innerText = amount.innerText- 1
// }
// script.src = 'http://stu.com:8002/pay?callback=' + functionName
// document.body.appendChild(script)
// script.onload = function(e){ // 状态码是 200~299 则表示成功
// e.currentTarget.remove()
// delete window[functionName] // 请求完了就干掉这个随机函数
// }
// script.onerror = function(e){ // 状态码大于等于 400 则表示失败
// e.currentTarget.remove()
// delete window[functionName] // 请求完了就干掉这个随机函数
// }
// })
</script>
</body>
</html>
以下为简单的server.js代码
var http = require('http')
var fs = require('fs')
var url = require('url')
var port = process.argv[2]
if(!port){
console.log('请指定端口号好不啦?\nnode server.js 8888 这样不会吗?')
process.exit(1)
}
var server = http.createServer(function(request, response){
var parsedUrl = url.parse(request.url, true)
var pathWithQuery = request.url
var queryString = ''
if(pathWithQuery.indexOf('?') >= 0){ queryString = pathWithQuery.substring(pathWithQuery.indexOf('?')) }
var path = parsedUrl.pathname
var query = parsedUrl.query
var method = request.method
/******** 从这里开始看,上面不要看 ************/
console.log('存在监听' + pathWithQuery)
if(path === '/'){ // 如果用户请求的是 / 路径
var string = fs.readFileSync('index.html','utf8') // 就读取 index.html 的内容
var amount=fs.readFileSync('db','utf8')
string=string.replace('&&&amount&&&',amount)
response.setHeader('Content-Type', 'text/html;charset=utf-8') // 设置响应头 Content-Type
response.write(string) // 设置响应消息体
response.end()
}else if(path==='/pay'){
var amount=fs.readFileSync('db','utf8')
var newAmount=amount-1
fs.writeFileSync('db',newAmount)
response.setHeader('Content-Type','application/javascript')
response.write(`
${query.callback}.call(undefined,'success')
`)
response.end()
}
else{
response.statusCode = 404
response.setHeader('Content-Type', 'text/html;charset=utf-8')
response.write('呜呜呜')
response.end()
}
/******** 代码结束,下面不要看 ************/
})
server.listen(port)
console.log('监听 ' + port + ' 成功\n请用在空中转体720度然后用电饭煲打开 http://localhost:' + port)
注意:运行时需要同时打开请求的服务器和本地服务器,不然将无法访问
运行命令为:node server 8888//假设端口为8888
网友评论