• JSONP与CORS原理与示例


     jQuery实现JSONP

    $.getJSON实现跨域
    
    $.getJSON("http://localhost:8080/bean?callback=?", {id:2,name:'李四',sex:'男'},
    
        function(data) {
    
    alert(data.id+data.name+data.sex);
    
    });
    
     
    
    使用jquery插件jquery.jsonp.js实现跨域
    
    $.jsonp({
    
     url: 'http://localhost:8080/bean?callback=?',
    
     "success": function(data) {
    
      console.log(data.id+data.name+data.sex);
    
     },
    
     "error": function(d,msg) {
    
       console.log(data)
    
     }
    
    });
    View Code

    JSONP只支持GET请求,不支持POST请求。

    JSONP的原型:创建一个回调函数,然后在远程服务上调用这个函数并且将JSON 数据形式作为参数传递,完成回调。

    将JSON数据填充进回调函数,这就是JSONP的JSON+Padding的含义。

    原生javascript实现JSONP

    <button onclick="f()">sendAjax</button>
    
    <script>
        function addScriptTag(src){
             var script = document.createElement('script');
             script.setAttribute("type","text/javascript");
             script.src = src;
             document.body.appendChild(script);
             document.body.removeChild(script);
        }
    
    
        function func(name){
            alert("hello"+name)
        }
    
        function f(){
             addScriptTag("http://127.0.0.1:7766/SendAjax/")
        }
    </script>
    
    # =============================http://127.0.0.1:7766/
    from django.views.decorators.csrf import csrf_exempt
    
    @csrf_exempt
    
    
    def SendAjax(request):
    
        import json
    
        print("++++++++")
        # dic={"k1":"v1"}
        return HttpResponse("func('yuan')")  # return HttpResponse("func('%s')"%json.dumps(dic))
    View Code

     jQuery中用$.ajax实现JSONP

    此外,如果说我们想指定自己的回调函数名,或者说服务上规定了固定回调函数名,我们可以使用$.ajax方法来实现,如下:
    <script>
    
        function f(){
              $.ajax({
                    url:"http://127.0.0.1:7766/SendAjax/",
                    dataType:"jsonp",
                    jsonp: 'callbacks',
                    jsonpCallback:"SayHi"
               });
    
           }
    
        function SayHi(arg){
                    alert(arg);
                }
    
    </script>
    //或者:通过回调函数来处理:
    
    <script>
    
        function f(){
    
                $.ajax({
                   url:"http://127.0.0.1:7766/SendAjax/",
                   dataType:"jsonp",            //必须有,告诉server,这次访问要的是一个jsonp的结果。
                   jsonp: 'callbacks',          //jQuery帮助随机生成的:callbacks="wner"
                   success:function(data){
                       alert("hi "+data)
                  }
             });
    
           }
    
    </script>
    View Code

      jsonp: 'callbacks'就是定义一个存放回调函数的键,jsonpCallback是前端定义好的回调函数方法名'SayHi',

    server端接受callback键对应值后就可以在其中填充数据打包返回了; 

    jsonpCallback参数可以不定义,jquery会自动定义一个随机名发过去,那前端就得用回调函数来处理对应数据了。
    利用jQuery可以很方便的实现JSONP来进行跨域访问。

    跨域资源共享 CORS

    CORS与JSONP的使用目的相同,但是比JSONP更强大。

    CORS需要浏览器和服务器同时支持。目前,所有浏览器都支持该功能,IE浏览器不能低于IE10。

    整个CORS通信过程,都是浏览器自动完成,不需要用户参与。对于开发者来说,

    CORS通信与同源的AJAX通信没有差别,代码完全一样。

    浏览器一旦发现AJAX请求跨源,就会自动添加一些附加的头信息,有时还会多出一次附加的请求,但用户不会有感觉。

    因此,实现CORS通信的关键是服务器。只要服务器实现了CORS接口,就可以跨源通信。

    两种请求

    浏览器将CORS请求分成两类:简单请求(simple request)和非简单请求(not-so-simple request)。

    只要同时满足以下两大条件,就属于简单请求。

    (1) 请求方法是以下三种方法之一:
    HEAD
    GET
    POST
    (2)HTTP的头信息不超出以下几种字段:
    Accept
    Accept-Language
    Content-Language
    Last-Event-ID
    Content-Type:只限于三个值application/x-www-form-urlencoded、multipart/form-data、text/plain

    凡是不同时满足上面两个条件,就属于非简单请求。

    浏览器对这两种请求的处理,是不一样的。

    * 简单请求和非简单请求的区别?
    
       简单请求:一次请求
       非简单请求:两次请求,在发送数据之前会先发一次请求用于做“预检”,只有“预检”通过后才再发送一次请求用于数据传输。
    * 关于“预检”
    
    - 请求方式:OPTIONS
    - “预检”其实做检查,检查如果通过则允许传输数据,检查不通过则不再发送真正想要发送的消息
    - 如何“预检”
         => 如果复杂请求是PUT等请求,则服务端需要设置允许某请求,否则“预检”不通过
            Access-Control-Request-Method
         => 如果复杂请求设置了请求头,则服务端需要设置允许某请求头,否则“预检”不通过
            Access-Control-Request-Headers

    支持跨域,简单请求

    服务器设置响应头(每次回应都必定包含的):Access-Control-Allow-Origin = '域名' 或 '*'

    支持跨域,复杂请求

    由于复杂请求时,首先会发送“预检”请求,如果“预检”成功,则发送真实数据。

    • “预检”请求时,允许请求方式则需服务器设置响应头:Access-Control-Allow-Methods
    • “预检”请求时,允许请求头则需服务器设置响应头:Access-Control-Allow-Headers

    发送Cookie

    如果要把Cookie发到服务器,一方面要服务器同意,指定Access-Control-Allow-Credentials字段。

    Access-Control-Allow-Credentials: true
    

    另一方面,开发者必须在AJAX请求中打开withCredentials属性。

    var xhr = new XMLHttpRequest();
    xhr.withCredentials = true;

    需要注意的是,如果要发送Cookie,Access-Control-Allow-Origin就不能设为星号,
    必须指定明确的、与请求网页一致的域名。
    同时,Cookie依然遵循同源政策,只有用服务器域名设置的Cookie才会上传,其他域名的Cookie并不会上传,
    且(跨源)原网页代码中的document.cookie也无法读取服务器域名下的Cookie。
  • 相关阅读:
    SQL Server(00):分析函数
    SQL Server(00):序列SEQUENCE
    .NET Standard 、.NET Core、 .NET Framework的区别
    电脑音频播放器 foobar2000
    JavaScript:highcharts图表
    SQL Server(00):带有OUTPUT的INSERT,DELETE,UPDATE
    [开发笔记]-js判断用户的浏览设备是移动设备还是PC
    [开发笔记]-获取天气数据接口
    [开发笔记]-控制Windows Service服务运行
    C#程序调用cmd执行命令
  • 原文地址:https://www.cnblogs.com/hongdoudou/p/12677104.html
Copyright © 2020-2023  润新知