I have the following code:
// in a service
downloadCSV(): Observable<Blob> {
return this.httpClient.get(`${apiUrl}/a.csv`, {responseType: 'blob'});
}
// in component
onDownloadClicked(event: MouseEvent) {
this.downloading = true;
this.service.downloadCSV()
.pipe(finalize(() => this.downloading = false))
.subscribe(
(data: Blob) => {
console.log(data);
},
(error) => {
console.error(error);
alert('Sorry, something wet wrong. Try again.');
},
() => {
console.log('completed!');
}
);
}
The data is logged correctly but 'completed!' is not logged and finalize is never called.
Edit:
So on further investigation, it seems the issue is related to an interceptor which adds an auth header.
If the interceptor is bypassed (and auth disabled on the server) the observable completes without error.
I don't understand why this is happening though. Possibly something related to the fact the request is cloned?
//interceptor code
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
let scope: string;
// only inject tokens for the following scopes
if (req.url.indexOf('https://graph.microsoft.com') === 0) {
scope = 'https://graph.microsoft.com';
}
else if (req.url.indexOf('https://management.azure.com') === 0) {
scope = 'https://management.azure.com';
}
else if (req.url.indexOf(environment.apiUrl) === 0) {
scope = environment.appId;
}
if (scope) {
return this.authService.getToken(scope).pipe(
switchMap((token) => {
let newReq;
if (token) {
const JWT = `Bearer ${token}`;
newReq = req.clone({
setHeaders: {
Authorization: JWT,
}
});
}
return next.handle(newReq || req);
})
);
}
else {
return next.handle(req);
}
}
HttpClient#get
with{ responseType: 'blob' }
and afinalize
in thepipe
. – Mehala