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

NestJS后端传输至Angular前端的图片无法在浏览器显示如何解决?

问题描述

从NestJS后端向Angular前端传输图片时,图片无法在浏览器中正常展示。
在此输入图片描述

实现逻辑为:前端向后端发送携带服务器文件路径(例如:C:\MyFolder\MyFile.png)的请求,后端读取对应图片后返回流给前端,前端将Blob转换为图片资源后,赋值给img元素的src属性完成渲染。

原有代码实现

后端控制器代码

@HttpCode(201)
@Get(':imageUrl')
@Header('Content-Type', 'image/png')
getFile(@Param('imageUrl')imageUrl: string) {
    imageUrl = atob(imageUrl);
    return fs.createReadStream(imageUrl);
}

前端代码

语言选择器TS代码

currentLanguage: ApplicationLanguage;
availableLanguages: ApplicationLanguage[];

constructor(private readonly _languageProvider: CultureProviderService,
          private readonly _imageLoader: ImageService) {
    this.currentLanguage = _languageProvider._currentLanguage;
    _languageProvider.languageChanged.subscribe(
      newLanguage => {
        this.currentLanguage = newLanguage;
      }
    )
}
ngOnInit(): void {
    this._languageProvider.getAllAvailableLanguages().subscribe(
      (languages: ApplicationLanguage[]) => {
        this.availableLanguages = languages;
        languages.forEach((language: ApplicationLanguage) => {
          this._imageLoader.getImage(language.flagIcon).subscribe(
            imgBlob => {
              this._imageLoader.createImageFromBlob(imgBlob).then(
                result => {
                  language.image = result;
                },
                err => {
                  console.log(err);
                }
              )
            }
          );
        });
      },
      err => {
        console.log(err);
      }
    );
}

图片加载服务代码

constructor(private readonly _http: HttpClient,
          private domSanitizer: DomSanitizer) { }

getImage(imageUrl: string): Observable<Blob> {
    return this._http.get(`${environment.machineServerUrl}/file/${btoa(imageUrl)}`, { responseType: 'blob' });
}

createImageFromBlob(imageUrl: Blob): Promise<SafeUrl> {
    return new Promise<SafeUrl>((resolve, reject) => {
      const reader = new FileReader();
      reader.addEventListener(
        "load",
        () => {
          resolve(this.domSanitizer.bypassSecurityTrustUrl(reader.result as string));
        }
      );

      if (imageUrl) {
        reader.readAsDataURL(imageUrl);
      } else {
        reject();
      }
    });
}

HTML代码

<div>
  <mat-selection-list (selectionChange)="changeLanguage($event)"
                      [multiple]="false">
    <mat-list-option  *ngFor="let language of availableLanguages"
                      [value]="language"  [selected] ="isSelected(language)">
      <img [src]="language.image" height="70px" width="70px" alt="国旗">
    </mat-list-option>
  </mat-selection-list>
</div>
解决方案

问题出在低版本NestJS无法直接正确处理返回的文件流,需按以下步骤修改:

  1. 升级NestJS版本至v8及以上,执行命令:nest update --force。如果升级失败,可以删除dist、node_modules和package-lock.json文件,用v8以上版本的NestJS CLI新建项目,用新生成的package.json覆盖原有项目的对应文件完成升级。
  2. 修改后端控制器代码,使用StreamableFile包装返回的文件流:
@HttpCode(201)
@Get(':imageUrl')
@Header('Content-Type', 'image/png')
getFile(@Param('imageUrl')imageUrl: string): StreamableFile {
  imageUrl = Buffer.from(imageUrl, 'base64').toString();

  const file = createReadStream(imageUrl);
  return new StreamableFile(file);
}

内容的提问来源于stack exchange,提问作者nkoniishvt

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.06 09:00:02