Angular使用自定义Pipe显示base64图片时src出现[object Object]报错排查
问题根因
你当前的代码存在两个核心问题:
transform方法直接返回了subscribe()调用的结果,这个返回值是Subscription类型的订阅对象,不是处理后的安全图片地址,所以赋值给src时自动转字符串就会显示[object Object]- 普通同步管道无法直接处理异步请求的返回值,你在subscribe回调里return的图片地址根本不会被模板接收到
修复方案
方法1:管道返回Observable配合async管道使用
首先修改管道代码,不要直接订阅,返回Observable并做安全处理:
import { HttpClient } from '@angular/common/http'; import { Pipe, PipeTransform } from '@angular/core'; import { ItemMaster } from '@cust-custap/core/http/item-master/item-master.service'; import { DomSanitizer, SafeResourceUrl } from '@angular/platform-browser'; import { map, Observable } from 'rxjs'; @Pipe({ name: 'getImageUrl', // ID不变时不会重复触发请求,保持纯管道即可 pure: true }) export class GetImageUrlPipe implements PipeTransform { constructor( private httpClient: HttpClient, private itemMasterService :ItemMaster, public sanitizer:DomSanitizer ) {} transform(value: any, id: any): Observable<SafeResourceUrl> { return this.itemMasterService.getItemImage(id).pipe( map((data:any) => { return this.sanitizer.bypassSecurityTrustResourceUrl('data:image/png;base64,'+data); }) ); } }
然后修改HTML模板,在管道后追加async管道处理异步值:
<!-- HTML part--> <div *ngFor="let product_catalog of result; let i= index;"> <img class="card-img img-fluid" width="75" height="75" alt="" [src]="'' | getImageUrl: product_catalog.ID | async"> </div>
方法2:组件侧预加载所有图片地址(更推荐,避免管道重复请求)
如果列表数据量较大,在管道内逐一发请求可能会触发不必要的重复调用,建议在组件获取result列表后,统一遍历请求所有图片地址,挂载到product_catalog对象上,模板直接绑定即可:
// 组件侧代码示例 this.result = 后端返回的商品列表; this.result.forEach(item => { this.itemMasterService.getItemImage(item.ID).subscribe(data => { item.imgUrl = this.sanitizer.bypassSecurityTrustResourceUrl('data:image/png;base64,'+data); }) })
模板直接绑定预加载的地址:
<img [src]="product_catalog.imgUrl">
额外注意事项
- 确保
getItemImage接口返回的是纯base64字符串,没有额外的data:image/png;base64,前缀,避免重复拼接导致地址失效 - 如果图片格式不固定为png,可以根据接口返回的Content-Type动态设置MIME类型,兼容性更好
内容的提问来源于stack exchange,提问作者Kapil Soni
相关产品推荐
相关产品推荐

