I want to upload few images and I have code as below. It returns the download link, but for only one image. How can I get a list of links to uploaded images?
constructor(private storage: AngularFireStorage, public afs: AngularFirestore, ) {
this.files = this.afs.collection('files').valueChanges();
}
uploadFile(event) {
// reset the array
this.uploads = [];
const filelist = event.target.files;
const allPercentage: Observable<number>[] = [];
for (const file of filelist) {
const filePath = `${file.name}`;
const fileRef = this.storage.ref(filePath);
const task = this.storage.upload(filePath, file);
const _percentage$ = task.percentageChanges();
allPercentage.push(_percentage$);
// observe percentage changes
this.uploadPercent = task.percentageChanges();
// get notified when the download URL is available
task.snapshotChanges().pipe(
finalize(() => {
this.downloadURL = fileRef.getDownloadURL();
})
).subscribe();
// this.downloadURLs.push(this.downloadURL);
}
}
uploadFile(files) {
//console.log(this.uploadService.uploadFile(file));
this.uploadService.uploadFile(files);
}
<ion-item>
<ion-input type="file" (change)="uploadFile($event)" multiple="multiple"></ion-input>
</ion-item>
<button (click)="onAddItem()" ion-button block>Добавить</button>
Easy way: Clear this.downloadURLs
before uploaded, then add url in finalize
step
uploadFile(event) {
// reset the array
this.uploads = [];
this.downloadURLs = [];
const filelist = event.target.files;
const allPercentage: Observable<number>[] = [];
for (const file of filelist) {
const filePath = `${file.name}`;
const fileRef = this.storage.ref(filePath);
const task = this.storage.upload(filePath, file);
const _percentage$ = task.percentageChanges();
allPercentage.push(_percentage$);
// observe percentage changes
this.uploadPercent = task.percentageChanges();
// get notified when the download URL is available
task.snapshotChanges().pipe(
finalize(() => {
fileRef.getDownloadURL().subscribe((url) => {
this.downloadURLs = this.downloadURLs.concat([url]);
});
})
).subscribe();
// this.downloadURLs.push(this.downloadURL);
}
}
Rxjs way: First combine all latest result, then subscribe to assign results. Note: You can use forkJoin
too
import { combineLatest, from } from 'rxjs';
import { map, filter } from 'rxjs/operators';
...
uploadFile(event) {
// reset the array
this.uploads = [];
const filelist = event.target.files;
const allPercentage: Observable<number>[] = [];
const downloadUrls$ = filelist.map((file) => {
const filePath = `${file.name}`;
const fileRef = this.storage.ref(filePath);
const task = this.storage.upload(filePath, file);
const _percentage$ = task.percentageChanges();
allPercentage.push(_percentage$);
// observe percentage changes
this.uploadPercent = task.percentageChanges();
// get notified when the download URL is available
return task.snapshotChanges().pipe(
filter((task) => task.state === this.storage.TaskState.SUCCESS)
switchMap(() => from(fileRef.getDownloadURL()))
)
});
combineLatest(...downloadUrls$)
.subscribe((urls) => this.downloadURLs = urls)
}