You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Angular中从ASP.NET Core API下载foo.txt文件

解决Angular中无法接收文件流并实现下载的问题

核心问题

Angular HTTP请求默认响应类型为JSON,后端返回的是文件流(Blob),若不指定响应类型会导致解析失败,无法进入成功回调;同时当前前端请求未传入后端要求的file参数,也会影响请求有效性。


步骤1:修正Angular服务层的请求配置

修改contractAttachementsService中的downloadFile方法,指定响应类型为blob,并传入file参数:

import { HttpClient } from '@angular/common/http';

@Injectable({ providedIn: 'root' })
export class ContractAttachementsService {
  constructor(private http: HttpClient) {}

  downloadFile(file: string) {
    // 替换为你的实际API基础路径
    return this.http.get(`/api/download/contractAttachment/${file}`, {
      responseType: 'blob' // 关键:明确指定响应类型为Blob
    });
  }
}

步骤2:实现组件中的文件下载逻辑

在组件的download方法中,接收Blob后通过创建临时DOM元素触发浏览器下载:

download(file: string) {
  this.contractAttachementsService.downloadFile(file).subscribe(blob => {
    // 创建Blob临时URL
    const blobUrl = window.URL.createObjectURL(blob);
    // 创建隐藏的a标签
    const downloadLink = document.createElement('a');
    downloadLink.href = blobUrl;
    // 设置下载文件名(可手动指定,或从后端响应头获取)
    downloadLink.download = 'foo.txt';
    // 触发点击下载
    document.body.appendChild(downloadLink);
    downloadLink.click();
    // 清理资源
    window.URL.revokeObjectURL(blobUrl);
    document.body.removeChild(downloadLink);
  }, error => {
    console.log(error);
  });
}

可选优化:从后端响应头动态获取文件名

如果需要后端返回动态文件名,可修改ASP.NET Core后端代码添加响应头:

// GET api/download/contractAttachment
[HttpGet("download/{file}")]
public IActionResult GetFileAsync(string file)
{
    var fileContent = Encoding.ASCII.GetBytes("foo");
    var result = File(fileContent, "text/plain", "foo.txt");
    // 添加响应头传递文件名
    Response.Headers.Add("Content-Disposition", $"attachment; filename=\"foo.txt\"");
    return result;
}

同时需在ASP.NET Core的CORS配置中暴露该响应头,允许前端读取:

// 在Program.cs/Startup.cs中配置CORS
builder.Services.AddCors(options =>
{
    options.AddPolicy("AllowDownload", policy =>
    {
        policy.AllowAnyOrigin()
              .AllowAnyMethod()
              .AllowAnyHeader()
              .WithExposedHeaders("Content-Disposition"); // 暴露自定义响应头
    });
});

app.UseCors("AllowDownload");

前端修改为从响应头提取文件名:

download(file: string) {
  this.contractAttachementsService.downloadFile(file).subscribe({
    next: (blob) => {
      const blobUrl = window.URL.createObjectURL(blob);
      const downloadLink = document.createElement('a');
      downloadLink.href = blobUrl;
      
      // 从响应头解析文件名
      const contentDisposition = this.httpResponse.headers.get('Content-Disposition');
      let filename = 'default.txt';
      if (contentDisposition) {
        const match = contentDisposition.match(/filename="?([^"]+)"?/);
        if (match?.length > 1) filename = match[1];
      }
      
      downloadLink.download = filename;
      document.body.appendChild(downloadLink);
      downloadLink.click();
      window.URL.revokeObjectURL(blobUrl);
      document.body.removeChild(downloadLink);
    },
    error: (err) => console.log(err)
  });
}

内容的提问来源于stack exchange,提问作者J.C

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.24 18:27:22