【问题标题】:Getting Angularjs $http post response as file result获取 Angularjs $http 后响应作为文件结果
【发布时间】:2017-02-28 22:17:27
【问题描述】:

我的 web api 有一个很长的内容请求参数。所以我需要发送一个 POST 请求。我的 api 正在创建一个 PDF 文件作为响应。但我无法使用 angularjs $http 提供程序获得结果。

var req = {
  method: 'POST',
  url: 'http://myapi.com/api/renderfile',
  data: { 
       p1: 'very long text....' ,
       p2: 'another very long text....',
       p3: 'another very long text....' 
  }
}

$scope.isLoading = true;

$http(req).then(function(response){

       // response is file result how can I save it ???

       $scope.isLoading = false;
   }, function(){
       $scope.isLoading = false;
   });

我无法在客户端保存文件响应?

回复是这样的:

当我使用 FileReader 时

 new FileReader().readAsDataURL(new Blob([response.data], {type:'application/pdf'}));

弹出窗口出现在浏览器上:

但是文件是空的。

【问题讨论】:

  • 响应内容类型是什么?
  • 你真的需要为此通过 AJAX 吗?我认为一种常见的方法是返回一个指向远程仓库的链接,用户可以在其中下载文件并让浏览器处理下载。
  • “无法得到结果”是什么意思?响应对象中有什么?您收到什么错误消息?

标签: angularjs


【解决方案1】:

如果您的响应中有文件内容,您可以强制浏览器下载此文件。

var reader = new FileReader();

$http(req).then(function(response){
   reader.readAsDataURL(new Blob([response.data], {type:'application/pdf'}));
});

reader.onload = function(e) { 
    window.open(decodeURIComponent(reader.result), '_self', '', false); 
}

但首选的解决方案是在您的响应中包含 location 标头以及文件链接。因此,您只需导航到此链接即可强制浏览器下载。

建议的解决方案仅适用于 HTML5 浏览器。

【讨论】:

  • 酷!从来没有这样想过..我曾经在需要下载文件时创建表单。 :P
  • @atulquest93 很有趣。你如何用表格下载?我的意思是当你有文件内容的 AJAX 响应时?你能指出一些资源或源代码吗?
  • @bookmarker,使用FileReader时,请参考response.data。我已经更新了代码。
  • 我更新了,但错误是:无法在“FileReader”上执行“readAsDataURL”:参数 1 不是“Blob”类型。
  • 看来您的数据类型不正确。需要转换成Blob => new Blob([response.data], {type:'application/pdf'})。我已经更新了示例
【解决方案2】:

使用 AngularJS 下载二进制文件

下载二进制文件时,设置 XHR 的responseType 属性很重要。

var config = { responseType: 'blob' }

var httpPromise = $http.get(url, config);

httpPromise.then(function (response) {
    $scope.data = response.data;
});

欲了解更多信息,请参阅MDN XHR API - ResponseType.


创建一个下载按钮

这是一个下载按钮的示例,该按钮在从服务器加载数据后变为活动状态:

<a download="data_{{files[0].name}}" xd-href="data">
  <button ng-disabled="!data">Download</button>
</a>

xdHref指令

app.module("myApp").directive("xdHref", function() {
  return function linkFn (scope, elem, attrs) {
     scope.$watch(attrs.xdHref, function(newVal) {
       if (newVal) {
         elem.attr("href", newVal);
       }
     });
  };
});

DEMO on PLNKR.

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-11-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-03-13
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多