使用JS怎样实现最简单的跨域
有一天有人跑来跟我定方案,问我cors是什么原理,一脸懵逼,跨域我只知道jsonP啊,眼看一个装逼的机会就要失去了。
“我现在有点忙,待会找你”。
机智的我马上回到工位,百度百度百度。
同源策略
老生常谈了,不是我家的人,东西当然不能让你随便乱动。
非同源的脚本不能访问或者操作其他域的页面对象(如DOM等),同源策略要求三同, 即: 同域, 同协议, 同端口。
跨域方法
本文只介绍jsonP和cors。
jsonP
<!-- 开发环境版本,包含了用帮助的命令行警告 --><script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
这是vue文档中引入vue.js的方法,可以看到script标签可以直接去请求其他域的JS文件。既然这样,我们就能使用这个特性来实现跨域。
搭个简单服务器
用nodejs+express搭个简单服务器。几行代码足矣。
const express = require('express');const app = express(); app.get('/user',(req,res)=>{ console.log('user'); res.send(‘success’); }) app.listen(3000,()=>{ console.log('start'); });
启动服务器。然后写个测试函数,先试试ajax。
function getUserAjax(){ let xhr= new XMLHttpRequest(); xhr.open("GET","http://127.0.0.1:3000/user",true); xhr.send(); }
在chrome控制台下运行getUserAjax函数。
可以看到被拒绝了,浏览器没有成功拿到success。这个时候就需要用到jsonP了。因为script标签本身就是可以跨域请求JS文件的。
function getUser(){ let dom = document.createElement('script'); dom.src = "http://127.0.0.1:3000/user"; document.body.appendChild(dom); }
控制台下运行getUser()。
success没有定义。可见浏览器已经跨域获取到了‘success’。因为script标签加载的JS会立刻执行,而success没有被定义,所以报了这个错。这个时候已经很明了了。前端发请求时将函数名,例如callback传给后台,后台再返回这个函数,callback(info)。这样浏览器接受到数据后,会马上执行callback函数,就像回调函数一样。马上开始改装:
前端代码:
function callback(info){ alert(info); }function getUser(){ let dom = document.createElement('script'); dom.src = "http://127.0.0.1:3000/user?callback=callback"; //url上指明回调函数的名字 document.body.appendChild(dom); }
后台代码:
const express = require('express');const app = express(); app.get('/user',(req,res)=>{ let func = req.query.callback; res.send(func+'(' + '"success"'+')'); }); app.listen(3000,()=>{ console.log('start'); });
再次执行getUser();成功弹出了success。这就是jsonP的原理。后台返回一个JS函数,带上参数,调用前端准备好的函数。即实现了发请求和回调函数的效果。
cors
这个就更简单了。上面ajax跨域的时候报了这个错误 No 'Access-Control-Allow-Origin' header is present on the requested resource。
那服务器返回的时候带上‘'Access-Control-Allow-Origin' 就好了。他的意思是允许哪些源的请求。你虽然不是我家的人,但这次我信任你,给你个钥匙。
改装下后台代码:
const express = require('express');const app = express(); app.get('/user',(req,res)=>{ res.header("Access-Control-Allow-Origin", "*"); //设置返回数据的头,代表接受任意源的请求 res.send('success'); }); app.listen(3000,()=>{ console.log('start'); });
再在控制台调用上文的getUserAjax()。成功。前端都不用改代码。不过要注意的是cors不是所有的浏览器都会支持。
jsonP和cors比较
cors与jsonP的使用目的相同,但是比jsonP更强大。
jsonP只支持GET请求,cors支持所有类型的HTTP请求。jsonP的优势在于支持老式浏览器,以及可以向不支持cors的网站请求数据。
相信看了本文案例你已经掌握了方法,更多精彩请关注其它相关文章!
推荐阅读:
以上就是使用JS怎样实现最简单的跨域的详细内容,更多请关注其它相关文章!