I am not an expert with Rxjs. I have the following code. I am trying to upload multiple files and for each file, i want to base64 convert and have all the result in final array. Below code is not working and the finalize
is not invoked at all. Can anyone help me what the problem with my code?
private validateSelectedFiles(files: FileList): void {
this.spinnerService.show();
from(files)
.pipe(
concatMap(f => this.convertFile(f)),
finalize(() => {
console.log('finalize'); //not coming here
this.spinnerService.hide();
}),
scan((acc, curr) => {
acc.push(curr)
return acc;
}, [])
).subscribe(result => {
console.log('result', result); //Only once it is coming here
})
}
private convertFile(file: File): Observable<string> {
const result = new ReplaySubject<string>(1);
const reader = new FileReader();
reader.readAsBinaryString(file);
reader.onload = (event) => {
result.next(btoa(event.target.result.toString()))
};
return result;
}
Expected functionality:
- for each upload files, convert it to base64
- get the array of base64 converted result for further processing
Following code worked for me:
private convertAttachmentsToBase64(): void {
forkJoin(Array.from(this.addedFiles).map(file => this.convertFile(file)))
.pipe(
takeUntil(this.destroy$),
finalize(() => this.spinnerService.hide()),
)
.subscribe((result) => this.attachmentsToUpload = result);
}
// Convert file to Base64
private convertFile(file: File): Observable<AttachmentToUpload> {
const result = new Subject<AttachmentToUpload>();
const reader = new FileReader();
reader.readAsBinaryString(file);
reader.onload = (event) => {
result.next({
fileName: file.name,
data: btoa(event.target.result.toString())
})
result.complete();
};
return result;
}