下载PDF文件,Angular 6和Web API

13

我想使用Angular 6和Web API下载PDF文档。以下是代码实现:

mycomponent.ts

download(myObj: any) {
    this.testService.downloadDoc(myObj.id).subscribe(result => {

        var url = window.URL.createObjectURL(result);
        window.open(url);
        console.log("download result ", result);
    });
}

myService.ts

downloadDoc(Id: string): Observable<any> {
    let url = this.apiUrl + "api/myApi/download/" + Id;
    return this.http.get(url, { responseType: "blob" });
}

Web API服务

[HttpGet("download/{DocId}")]
    public async Task<HttpResponseMessage> GetDocument(string docId)
    {
        var docDetails = await _hoaDocs.GetDocumentDetails(docId).ConfigureAwait(false);
        var dataBytes = docDetails.Stream;
        var dataStream = new MemoryStream(dataBytes);

        var response = new HttpResponseMessage
        {
            StatusCode = HttpStatusCode.OK,
            Content = new StreamContent(dataStream)
        };

        response.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("attachment")
        {
            FileName = docDetails.File_Name
        };
        response.Content.Headers.ContentType = new MediaTypeHeaderValue("application/pdf");

        return response;
    }
执行以上代码时,未能下载 PDF,以下是记录在控制台中的结果对象。
download result  
Blob(379) {size: 379, type: "application/json"}
size:379
type:"application/json"
__proto__:Blob
4个回答

6
我假设您正在使用 .Net Core。
您的返回类型是 HttpResponseMessage。从 .Net Core 开始,应该是 IActionResult。
因此,在您的情况下,您将返回
return File(<filepath-or-stream>, <content-type>)

或者

您需要在Startup.cs文件中进行一项小的更改:

services.AddMvc().AddWebApiConventions();

那么,我不是100%确定,但你也必须更改路由:

routes.MapWebApiRoute("DefaultApi", "api/{controller}/{id?}");

是的,我正在使用.NET Core,你的建议解决了问题。 - Madhu

5
import { Injectable } from "@angular/core";
declare var $;

@Injectable()
export class DownloadFileService {

   save(file, fileName) {
       if (window.navigator.msSaveOrOpenBlob) {
        // IE specific download.
        navigator.msSaveBlob(file, fileName);
    } else {
        const downloadLink = document.createElement("a");
        downloadLink.style.display = "none";
        document.body.appendChild(downloadLink);
        downloadLink.setAttribute("href", window.URL.createObjectURL(file));
        downloadLink.setAttribute("download", fileName);
        downloadLink.click();
        document.body.removeChild(downloadLink);
     }
   }
}

感谢您的回复,当我尝试了建议的方法后,文档以json文件的形式下载。当我尝试将扩展名更改为.pdf并打开它时,出现了一个错误,指出“Reader无法打开'test.pdf',因为它不是支持的文件类型”。 - Madhu
您可以按照以下方式使用该服务,它将自动将数据下载为PDF文件: var yourPDFDataBlob = new Blob([从服务器获取的响应数据], { type: "application/pdf" }); downloadFileService.save(yourPDFDataBlob, pdf文件名 + ".pdf"); - anees

1

dataService.ts

  downloadNoteReceipt(notes_purchased_id: number):Observable<Blob>{    
        return this.httpClient.get(this.baseUrl + `receipt/notespurchasedreceipt/` + notes_purchased_id, { responseType: "blob" } );
      }

component.ts

  download(booking_id: number) {
    this.orderDetailsService.downloadNoteReceipt(booking_id).subscribe(res => {
      console.log(res);
      var newBlob = new Blob([res], { type: "application/pdf" });

      if (window.navigator && window.navigator.msSaveOrOpenBlob) {
        window.navigator.msSaveOrOpenBlob(newBlob);
        return;
    }
     // For other browsers: 
            // Create a link pointing to the ObjectURL containing the blob.
            const data = window.URL.createObjectURL(newBlob);

            var link = document.createElement('a');
            link.href = data;
            link.download = "receipt.pdf";
            // this is necessary as link.click() does not work on the latest firefox
            link.dispatchEvent(new MouseEvent('click', { bubbles: true, cancelable: true, view: window }));

            setTimeout(function () {
                // For Firefox it is necessary to delay revoking the ObjectURL
                window.URL.revokeObjectURL(data);
            }, 100);

    }, error => {
      console.log(error);
    })
  }

component.html

 <i class="fa fa-download" style="font-size:20px;color:purple" aria-hidden="true" (click)="download(row.booking_id)"></i>

1
在某些浏览器中,我们需要动态创建锚点标签并使其可点击以下载文件。以下是代码。
  const link = document.createElement('a');
  link.href = window.URL.createObjectURL(blob);
  link.download = filename;
  link.click();

希望这有所帮助。谢谢。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接