Angular 5中DomSanitizer处理图片资源的技术咨询
Angular 5中DomSanitizer处理Firestore动态图片资源的实践
我之前也碰到过一模一样的情况:从Firestore拉取集合后,用ngFor动态绑定[src]或者[style.background-image]时,Angular的安全机制会拦截这些资源。后来我封装了一个Image Sanitizer Service来统一处理,下面是具体的实现和使用方式:
1. 实现Image Sanitizer Service
首先创建一个可注入的服务,把DomSanitizer的处理逻辑封装起来,这样所有组件都能复用:
import { Injectable } from '@angular/core'; import { DomSanitizer, SafeResourceUrl, SafeStyle } from '@angular/platform-browser'; @Injectable({ providedIn: 'root' // 全局提供,所有模块都能直接注入 }) export class ImageSanitizerService { constructor(private sanitizer: DomSanitizer) {} // 处理img标签的[src]属性 sanitizeImageUrl(url: string): SafeResourceUrl { return this.sanitizer.bypassSecurityTrustResourceUrl(url); } // 处理背景图片的[style.background-image]属性 sanitizeBackgroundImage(url: string): SafeStyle { return this.sanitizer.bypassSecurityTrustStyle(`url('${url}')`); } }
这里要注意两个方法的区别:
bypassSecurityTrustResourceUrl用于资源类URL(比如图片、脚本的src)bypassSecurityTrustStyle用于CSS样式字符串,比如背景图的url语法
2. 在组件中使用服务
在需要动态加载图片的组件里注入这个服务,然后在模板的ngFor中直接调用对应的方法:
示例1:绑定img的[src]
<div *ngFor="let item of firestoreCollection$ | async"> <img [src]="imageSanitizer.sanitizeImageUrl(item.imageUrl)" alt="{{item.title}}" > </div>
示例2:绑定背景图
<div *ngFor="let item of firestoreCollection$ | async" [style.background-image]="imageSanitizer.sanitizeBackgroundImage(item.imageUrl)" > {{item.description}} </div>
一些关键注意事项
- 不要直接在模板里调用
DomSanitizer的方法,封装成服务更利于维护和复用 - 永远不要全局禁用Angular的安全机制,只对确认安全的资源进行标记
- 如果你的Firestore图片URL是经过验证的(比如只允许存储在你控制的存储桶里),那么这样的处理是安全的
内容的提问来源于stack exchange,提问作者Nicholas Pesa
相关产品推荐
相关产品推荐

