2
votes

The following service method returns an image (if one exists for the given parameter in the database) or a 404 error if the image does not exist:

public getLegendImage(id: string): Observable<Blob> {
    let params = new HttpParams();
    params = params.append('id', id);
    return <Observable<Blob>>this.http.get('service/getLegendImage', { params: params, responseType: 'blob'});
}

In my component I'm consuming it with an async pipe:

ngOnInit() {
   this.data = this.activeLayers.map(layer => ({ id: layer.id, name: layer.name, image$: this.getLayerImage$(layer.id)}));  
}

public getLayerImage$(layer: string): Observable<SafeUrl> {
    return this.layerService.getLegendImage(layer).map(blob =>  this.domSanitizer.bypassSecurityTrustUrl(window.URL.createObjectURL(blob)))
        .catch(err => Observable.of(-1));
}

And in the template:

  <div *ngFor="let layer of this.data">
      <b>{{ layer.name }}</b><br>
      <span class="legend-image"><img [attr.src]="(layer.image$ | async)" /></span>              
  </div>

However, I'm still getting uncaught 404 http exceptions when the webservice request return 404.

If I return "undefined" in the .catch() method, I get the following error:

You provided 'undefined' where a stream was expected. You can provide an Observable, Promise, Array, or Iterable.

The desired behaviour would be, that the image$ observable points to some default image in the assets of the client app if the service returns a 404 error. But I do not see how to do that :(

1
So you're getting 404 because your service isn't really returning an image. It is returning a 404 Status Code instead. As far as the catch goes, an elegant solution would be to have a custom 404 Not Found image present in your assets or hosted somewhere, and then in the catch block, instead of returning -1 or null or undefined, you return an Observable of that image path. - SiddAjmera

1 Answers

0
votes

i would assume that you want to redirect to a 404 page, in that case i would recommend to catch the error in the http call within the service. An example would be:

 return <Observable<Blob>>this.http.get('service/getLegendImage', { params: params, responseType: 'blob'}).pipe(
    catchError(() => {
     this.router.navigate(['/404']);
     return Observable.throw('Error 404');
    }));

If you dont want to redirect just delete the navigate code and catch the error in the component.