【问题标题】:Using JSONP when returning XML返回 XML 时使用 JSONP
【发布时间】:2011-03-27 00:20:23
【问题描述】:

我问过一个较早的question,这肯定很有帮助,并让我知道了 JSONP。但是,我看到我必须将 JSONP 指定为数据类型。现在,据我所知,这是返回数据的返回类型,即 XML。可以使用 JSONP 返回 XML,还是仅限于以 JSONP 格式返回?谢谢!

【问题讨论】:

    标签: javascript jquery xml jsonp


    【解决方案1】:

    由于它的工作方式,您只能使用 JSONP(而不是 XML)。 JSONP变成了这样:

    <script src="myPage?callback=myFunction" type="text/javscript">
    

    因此,当您获取内容时,它有效地这样做了:

    <script type="text/javascript">
      myFunction({ data: value, data2: value2 });
    </script>
    

    返回的是实际运行的 JavaScript,所以它不可能是 XML,你会得到各种各样的语法错误,正是你会这样做:

    <script type="text/javascript">
      <elem>
        <data>value</data>
        <data2>value2</data2>
      </elem>
    </script>
    

    您可以想象,JavaScript 解析器不会非常喜欢它,也不知道如何处理它。 jQuery 在大多数情况下可以毫无问题地解析 XML,但是如果您使用 JSONP 并且它用于跨域请求......那么 JSONP 是您唯一的选择,除非您在您的网站上编写了一个没有违反的代理页面同源策略规则,并将其用作代理来获取 XML。

    【讨论】:

    • 感谢您的帮助!如果我想将数据发布到 API而不 使用 JSONP,我可以将数据发布到 API,而不必担心奇怪的跨域内容对吗?感谢您的帮助,我是一个 php 人,Javascript/jQuery 对我来说仍然很新!基本上我正在尝试编写一个小部件以放在其他网站上,所以我仅限于 Javascript,并且不能使用任何服务器端。再次感谢!
    • @patricksweeney - 您可以发布是,但您不会收到回复,这是 来自 服务器的响应,而不是 POST to 您的浏览器阻止的服务器...POST 响应的内容将为空,这就是同源安全在每个主要浏览器中的工作方式。
    • 所以基本上我应该看看我们是否可以将服务器响应包装在 JSONP 中或使用代理,对吧?
    • @patricksweeney - 正确,这是您最好的两个解决方案 :)
    • 我正在尝试通过 json 获取 NexTrip API,但它返回了一个 XML 文件。我要疯了吗?
    【解决方案2】:

    这个想法是从服务器发回可执行代码。编写一个 jQuery 插件或扩展 ajax 函数以将 XML 字符串作为函数参数返回。

    myCallback("
      <root>
        <person>
          <first>John</first>
          <last>Doe</last>
        </person>
      </root>")
    

    插件会将此字符串解析为 XML 并将其返回给您的实际回调。就您的回调而言,它不知道string -&gt; xml 转换过程。

    这是一个现有的implementation

    jQuery 最理想的接口是,

    $.ajax({
        url: 'http://example.com/resource?type=xml',
        dataType: 'xmlp',
        success: function(xml) { .. }
    });
    

    但由于搞乱和重写jQuery.ajax 是有问题的,你可以把它写成一个单独的命名空间插件本身,它将在下面使用getScript

    $.myNamespace.ajax({
        ..
    });
    

    为此,您需要控制服务器。服务器必须知道请求了 XML,并以包含 XML 字符串作为参数的函数调用进行响应。假设您发送到远程服务器的回调名称是foo,服务器将必须响应如下内容:

    foo("<names><name>..</name></names>")
    

    我认为,如果您使用的是支持 E4X 的浏览器,则无需将 XML 包装在字符串中。服务器可以简单地将 XML 作为参数返回给回调函数:

    foo(
      <names>
        <name>John Doe</name>
      </names>
    )
    

    但不幸的是,E4X 尚未得到广泛支持。

    【讨论】:

    • 如果将dataType 设置为jsonp xml,jQuery 确实支持xmlp。根据文档:“从 jQuery 1.5 开始,jQuery 可以将数据类型从它在 Content-Type 标头中收到的内容转换为您需要的内容。例如,如果您希望将文本响应视为 XML,请使用“文本 xml”对于数据类型。您还可以发出 JSONP 请求,将其作为文本接收,并由 jQuery 解释为 XML:“jsonp text xml”。类似地,诸如“jsonp xml”之类的速记字符串将首先尝试从 jsonp 转换为xml,如果失败,则从 jsonp 转换为文本,然后从文本转换为 xml。”
    • @greg.kindel - 感谢您提供的信息。我会尝试更新答案,但我现在有点懒。
    【解决方案3】:

    您可以在/* comment */ 内部的Javascript 函数中编写XML,并使用functionname.toString() 方法将此函数转换为文本并解析“/*”和“*/”之间的文本使用 JSONPcallback 函数,适用于所有旧浏览器。示例 xml_via_jsonp.js

    function myfunc()
    {/*
    <xml>
    <div class="container">
            <div class="panel panel-info col-lg-10 col-lg-offset-1 added-panel">
                <div class="panel-heading">Random1 - Random2</div>
                <div class="panel-body">
                    <div>Random3</div>
                </div>
            </div>
        </div>
    </xml>
    */}
    
    function callback(func)
    {
    var myhtml = func.toString();
    var htmlstart = myhtml.indexOf('/*');
    var htmlend = myhtml.lastIndexOf('*/');
    return myhtml.substr(htmlstart+2, htmlend-htmlstart-2);
    }
    

    【讨论】:

    • 这是个糟糕的主意。
    • 你有什么更好的主意?
    • 您可以简单地将 XML 存储在一个字符串中。用xml_string 完全跳过整个func.toString()
    • 您必须在所有引号中添加斜杠,这会使 XML 难以阅读
    • 好吧,理想情况下,你会生成你的 XML 服务器端,序列化它,编码成 JSON 字符串,返回给客户端,然后客户端反序列化 JSON 字符串,然后得到 XML 字符串.
    猜你喜欢
    • 2012-09-02
    • 2012-04-15
    • 2011-03-01
    • 2013-11-14
    • 1970-01-01
    • 1970-01-01
    • 2013-01-11
    • 2014-05-26
    • 2013-05-21
    相关资源
    最近更新 更多