zoukankan      html  css  js  c++  java
  • 【JavaScript】--重点解析之跨域请求

    JSON

      JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式。

      JSON是用字符串来表示Javascript对象,例如可以在django中发送一个JSON格式的字符串给客户端Javascript,Javascript可以执行这个字符串,得到一个Javascript对象。

      json就是js对象的一种表现形式(字符串的形式)

    JSON对象语法

      json语法:

    • 数据在名称/值对中
    • 数据由逗号分隔
    • 花括号保存对象(对象需要使用大括号起来)
    • 方括号保存数组(数组使用中括号括起来)
    var person = {"name":"zhangSan", "age":"18", "sex":"male"};
    alert(person.name + ", " + person.age + ", " + person.sex);

    注意,key也要在双引号中!

    JSON值:

    • 数字  (整数或浮点数)
    • 字符串(在双引号中)
    • 逻辑值(true 或 false)
    • 数组   (在方括号中)
    • 对象   (在花括号中)
    • null
    var person = {"name":"alex", "age":"18", "sex":"male", "hobby":["girl", "movie", "travle"]};
    alert(person.name + ", " + person.age + ", " + person.sex + ", " + person.hobby);

    带有方法的JSON对象:

    var person = {"name":"alex",
                  "sex":"men",
                  "teacher":{
                     "name":"tiechui",
                      "sex":"half_men",
                  },
                  "bobby":['basketball','running'],
    
                   "getName":function() {return 80;}
                  };
    alert(person.name);
    alert(person.getName());
    alert(person.teacher.name);
    alert(person.bobby[0]);

    js接受python的json对象:

    在json的编码过程中,会存在从python原始类型向json类型的转换过程,具体的转换
        如下:
    
            python         -->        json
            dict                      object
            list,tuple                array
            str,unicode               string
            int,long,float            number
            True                      true
            False                     false
            None                      null

    js与django的交互

    def login(request):
        obj={'name':"alex111"}
        return render(request,'index.html',{"objs":json.dumps(obj)})
    #----------------------------------
     <script>
         var temp={{ objs|safe }}
         alert(temp.name);
         alert(temp['name'])
     </script>

    JSON与XML比较

    • 可读性:   XML胜出;
    • 解码难度:JSON本身就是JS对象(主场作战),所以简单很多;
    • 流行度:   XML已经流行好多年,但在AJAX领域,JSON更受欢迎。

    parse()和.stringify()

    parse用于从一个字符串中解析出json对象,如
    
    var str = '{"name":"yuan","age":"23"}'
    
    结果:
    
    JSON.parse(str)
    
    Object
    
    age: "23"
    name: "yuan"
    
    
    注意:单引号写在{}外,每个属性名都必须用双引号,否则会抛出异常。
    
    
    stringify()用于从一个对象解析出字符串,如
    
    var
     a = {a:1,b:2}
    
    结果:
    
    JSON.stringify(a)
    
    "{"a":1,"b":2}"

     跨域请求

      同源策略机制

      浏览器有一个很重要的概念——同源策略(Same-Origin Policy)。所谓同源是指,域名,协议,端口相同。不同源的客户端脚本(javascript、ActionScript)在没明确授权的情况下,不能读写对方的资源。

      简单的来说,浏览器允许包含在页面A的脚本访问第二个页面B的数据资源,这一切是建立在A和B页面是同源的基础上。

      如果Web世界没有同源策略,当你登录淘宝账号并打开另一个站点时,这个站点上的JavaScript可以跨域读取你的淘宝账号数据,这样整个Web世界就无隐私可言了。

      jsonp的js实现

       JSONP是JSON with Padding的略称。可以让网页从别的域名(网站)那获取资料,即跨域读取数据。

      它是一个非官方的协议,它允许在服务器端集成Script tags返回至客户端,通过javascript callback的形式实现跨域访问(这仅仅是JSONP简单的实现形式)。

      JSONP就像是JSON+Padding一样(Padding这里我们理解为填充)

    #---------------------------http://127.0.0.1:8001/login
    
     def login(request):
        print('hello ajax')
        return render(request,'index.html')
     #---------------------------返回用户的index.html
     <h1>发送JSONP数据</h1>
    
    
    <script>
        function fun1(arg){
            alert("hello"+arg)
        }
    </script>
    <script src="http://127.0.0.1:8002/get_byjsonp/"></script>
    
    #-----------------------------http://127.0.0.1:8002/get_byjsonp
    
    def get_byjsonp(req):
        print('8002...')
        return HttpResponse('fun1("苑昊")')

      这其实就是JSONP的简单实现模式,或者说是JSONP的原型:创建一个回调函数,然后在远程服务上调用这个函数并且将JSON 数据形式作为参数传递,完成回调。

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

      一般情况下,我们希望这个script标签能够动态的调用,而不是像上面因为固定在html里面所以没等页面显示就执行了,很不灵活。我们可以通过javascript动态的创建script标签,这样我们就可以灵活调用远程服务了。

    <script>
        function addScriptTag(src){
         var script = document.createElement('script');
             script.setAttribute("type","text/javascript");
             script.src = src;
             document.body.appendChild(script);
        }
        function fun1(arg){
            alert("hello"+arg)
        }
    
        window.onload=function(){
            addScriptTag("http://127.0.0.1:8002/get_byjsonp/")
        }
    </script>

       现在将你自己在客户端定义的回调函数的函数名传送给服务端,服务端则会返回以你定义的回调函数名的方法,将获取的json数据传入这个方法完成回调:

    <script>
        function addScriptTag(src){
         var script = document.createElement('script');
             script.setAttribute("type","text/javascript");
             script.src = src;
             document.body.appendChild(script);
        }
        function fetch(arg){
            alert("hello"+arg)
        }
    
        window.onload=function(){
            addScriptTag("http://127.0.0.1:8002/get_byjsonp?callback=fetch")
        }
        
    </script>
    
    #--------------------------------http://127.0.0.1:8002/get_byjsonp    
        def get_byjsonp(req):
    
        callback=req.GET.get('callback')
        print(callback)
        return HttpResponse('%s("yuan")'%callback)
    View Code

    jQuery对JSONP的实现

      jQuery框架也当然支持JSONP,可以使用$.getJSON(url,[data],[callback])方法

    <script type="text/javascript">
        $.getJSON("http://127.0.0.1:8002/get_byjsonp?callback=?",function(arg){
            alert("hello"+arg)
        });
    </script>

      结果是一样的,要注意的是在url的后面必须添加一个callback参数,这样getJSON方法才会知道是用JSONP方式去访问服务,callback后面的那个问号是内部自动生成的一个回调函数名。

      当然,如果说我们想指定自己的回调函数名,或者说服务上规定了固定回调函数名该怎么办呢?我们可以使用$.ajax方法来实现

    <script type="text/javascript" src="/static/jquery-2.2.3.js"></script>
    
    <script type="text/javascript">
       $.ajax({
            url:"http://127.0.0.1:8002/get_byjsonp",
            dataType:"jsonp",
            jsonp: 'callbacks',
            jsonpCallback:"fetch"
       });
        function fetch(arg){
            alert(arg);
        }
    </script>
     
    #--------------------------------- http://127.0.0.1:8002/get_byjsonp
     def get_byjsonp(req):
    
        callback=req.GET.get('callbacks')
        print(callback)
        return HttpResponse('%s("yuan")'%callback)
    View Code

    another way:

    <script type="text/javascript" src="/static/jquery-2.2.3.js"></script>
    
    <script type="text/javascript">
       $.ajax({
            url:"http://127.0.0.1:8002/get_byjsonp",
            dataType:"jsonp",
            jsonp: 'callbacks',
            success:function(data){
                alert(data)
            }
       });
    
    </script>
     #-------------------------------------http://127.0.0.1:8002/get_byjsonp
    def get_byjsonp(req):
    
        callback=req.GET.get('callbacks')
        print(callback) #jQuery223015502220591490135_1477560648881
    return HttpResponse("%s('yuan')"%callback)
    View Code

      没错,jsonpCallback就是可以指定我们自己的回调方法名fetch,远程服务接受callback参数的值就不再是自动生成的回调名,而是fetch。dataType是指定按照JSOPN方式访问远程服务。callback必须有,因为服务端根据它来去回调函数的名字,如果是自已定义的,那么就得有自定义的名字:jsonpCallback:"fetch";如果不加这个参数,则自动生成一个随机名字。

       利用jQuery可以很方便的实现JSONP来进行跨域访问。

    人生短短数十载,经不起几次重头再来
  • 相关阅读:
    VS1053 datasheet 解读笔记
    C# List Find方法
    git push & git pull 推送/拉取指定分支
    Python 匿名函数
    Python 函数
    java jdk安装与环境变量配置
    Anroid开发环境配置
    Asponse.Cell操作Excel
    C#调试DeBug
    Ext.gridPanel中内容对齐
  • 原文地址:https://www.cnblogs.com/bk770466199/p/6122533.html
Copyright © 2011-2022 走看看