如何使用 AngularJS 从外部 URL 获取 JSON 并在页面中显示 - 资源解释为脚本但使用 MIME 类型 text/html 传输

Posted

技术标签:

【中文标题】如何使用 AngularJS 从外部 URL 获取 JSON 并在页面中显示 - 资源解释为脚本但使用 MIME 类型 text/html 传输【英文标题】:How to use AngularJS to get JSON from external URL and display in page - Resource interpreted as Script but transferred with MIME type text/html 【发布时间】:2014-06-09 17:30:38 【问题描述】:

我正在尝试对 URL 进行 http 调用以获取 JSON 并将其显示在我的页面上。

JSON 看起来像这样:

"ticker":"high":484.01099,"low":470.37201,"avg":477.1915,"vol":2193393.03322,"vol_cur":4588.62668,"last":482.16,"buy":482.16,"sell":481.2,"updated":1398350394,"server_time":1398350394

代码如下。我读到我必须使用“JSONP”,但我不知道如何使用它。

<html ng-app>
    <body>
        <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.0-beta.6/angular.min.js"></script>
        <div id = "content" style="min-width: 1200px; max-width: 90%: margin-left: auto; margin-right: auto;">
            <div style="width: 520px; float: left;">
                <h4>Bot Summary:</h4>
            </div>
            <div  ng-controller="TickerControl" style="width: 680px; float: left;">
                <h4>Market Summary</h4>
                <p>Price = data </p>
            </div>
        </div>
        <div></div>

        <script type="text/javascript">

            function TickerControl($scope, $http, $templateCache) 
                $scope.method = 'JSONP';
                $scope.url = 'https://btc-e.com/api/2/btc_usd/ticker?callback=JSON_CALLBACK';

                $scope.getTicker = function() 
                  $scope.code = null;
                  $scope.response = null;

                  $http(method: $scope.method, url: $scope.url, cache: $templateCache).
                    success(function(data, status) 
                      $scope.status = status;
                      $scope.data = data;
                    ).
                    error(function(data, status) 
                      $scope.data = data || "Request failed";
                      $scope.status = status;
                  );
                ;

                            $scope.getTicker();
            

        </script>

    </body>
</html>

更新

我现在修改了我的代码以尝试执行 JSONP 请求。我收到以下错误:

Resource interpreted as Script but transferred with MIME type text/html: "https://btc-e.com/api/2/btc_usd/ticker?callback=angular.callbacks._0". angular.js:8582
Uncaught SyntaxError: Unexpected token : ticker:1

我似乎收到了短信。由于我无法控制服务器响应,我该如何将此文本解析为 JSON……甚至显示它……它可以在 chrome 开发环境中查看。

更新 2

显然这似乎是服务器配置不正确的问题。由于我无权访问它,因此能够仅接收文本并在客户端中解析它会很好!

【问题讨论】:

除非您的代码在 btc-e.com 上,否则您需要使用 JSONPcrossorigin AJAX 嗨@Valerji,谢谢这是我的理解。但我不确定如何使用 JSONP,我尝试在 URL 中添加“回调”来做一些事情,但我遇到了其他错误。 这个&lt;p&gt;Price = getTicker() &lt;/p&gt;不断调用一个连接到api的方法,这就是它挂起的原因,就像一个无限循环 你删除了&lt;p&gt;Price = getTicker() &lt;/p&gt; 你可以做 &lt;p&gt;Price = data &lt;/p&gt; 或类似的东西,所以它从范围加载一些数据,而不是一遍又一遍地调用函数 【参考方案1】:

在进行了更多研究并尝试了不同的方法后,我很遗憾地通知您,您想要实现的目标无法实现。

出于测试目的,我向https://btc-e.com/api/2/btc_usd/ticker?callback=JSON_CALLBACK 发送了一个 GET 请求,并在响应标头中显示

内容类型 → 文本/html;字符集=utf-8

因为你做跨域调用,又无权访问服务器,所以必须使用jsonp。但 jsonp 不适用于 text/html 内容。这与错误有关

资源解释为脚本,但使用 MIME 类型 text/html 传输

因此,即使响应看起来像有效的 JSON,您的客户端应用程序也不会这样处理。

要解决此问题,您必须在服务器上添加正确的 Content-Type 标头,但您无权访问它。

引用this related question:

只有当服务器正确地将响应嵌入到 javascript 函数调用中时,才能使用 jsonp。


总结一下:

你应该

通过配置服务器来允许跨域调用 通过配置服务器发回正确的内容类型标头

很遗憾,您无法访问服务器。

请注意,这不是您的错。是因为服务器配置不正确。

【讨论】:

感谢蒂姆的回答。所以不可能只获取文本并在客户端解析它? :O 不,因为 jsonp 期望的内容不同于 text/html 真可惜。我将不得不运行我自己的 .net 服务器,它可以获取和解析 JSON 并向它发出请求! @ArmenSafieh-Garabedian 是的 :-) 祝你好运。如果问题已解决,请将答案标记为已接受【参考方案2】:

如果响应包含纯文本,您可以使用“angular.fromJson(data)”对其进行解析。使用 GET 请求获取数据(并确保响应实际上不包含 HTML 代码)。

【讨论】:

好吧,它应该是 JSON,我不知道为什么我会收到该错误消息。我怎样才能将响应打印到控制台? 即使您“获取”数据?您也可以尝试显式设置 Content-Type,详情请参阅 docs.angularjs.org/api/ng/service/$http GET 根本不起作用,因为“请求的资源上不存在 'Access-Control-Allow-Origin' 标头。因此不允许访问 Origin 'null'。” 好吧,您可以尝试将 JSONP 请求的 Content-type 强制为 text/html,但这有点难看.. 现阶段我愿意尝试任何事情!

以上是关于如何使用 AngularJS 从外部 URL 获取 JSON 并在页面中显示 - 资源解释为脚本但使用 MIME 类型 text/html 传输的主要内容,如果未能解决你的问题,请参考以下文章

从 angularJS 部分链接到具有不同域的外部 URL

使用 AngularJS 从 JSON 响应中获取图像 url

如何使用 angularjs 从 url 下载(保存)图像到我们的相册中?

AngularJS如何调用外部接口?

Angularjs:如何将图层添加到外部模板中?

如何使用 c# asp.net 从 url 获取数据?