Reputation: 63
Can someone assist me with revising the code so it will wait for the upload to finish then save the image urls to firestore? I'm new to async and await and can't seem to figure it out. The fileDownloadUrl
is still empty even if I do the saving to firestore inside the Promise.all(promises).then()
:
cxonst promises = [];
const fileDownloadUrl = [];
pictures.forEach(file => {
const uploadTask =
firebase
.storage()
.ref()
.child(`img/upl/${file.data.name}`)
.put(file.uploadTask);
promises.push(uploadTask);
uploadTask.on(
firebase.storage.TaskEvent.STATE_CHANGED,
snapshot => {
const progress = Math.round((snapshot.bytesTransferred /
snapshot.totalBytes) * 100);
if (snapshot.state === firebase.storage.TaskState.RUNNING) {
console.log(`Progress: ${progress}%`);
}
},
error => console.log(error.code),
async () => {
const downloadURL = await
uploadTask.snapshot.ref.getDownloadURL();
fileDownloadUrl.push(downloadURL);
}
);
});
Promise.all(promises)
.then(() => {
db
.collection("properties")
.add({
timestamp: firebase.firestore.FieldValue.serverTimestamp(),
title: title,
description: description,
pictures: fileDownloadUrl,
user: user.uid
})
})
.catch(err => console.log(err));
Upvotes: 0
Views: 851
Reputation: 599956
While you are waiting for the promises of the put
calls to complete, you're then using the uploadTask.on()
to determine the download URL. Since this on
is not part of the promise, there is no guarantee they're in sync.
A simpler and working approach should be:
const promises = pictures.map(file => {
const ref = firebase.storage().ref().child(`img/upl/${file.data.name}`);
return ref
.put(file.uploadTask)
.then(() => ref.getDownloadURL())
});
Promise.all(promises)
.then((fileDownloadUrls) => {
db
.collection("properties")
.add({
timestamp: firebase.firestore.FieldValue.serverTimestamp(),
title: title,
description: description,
pictures: fileDownloadUrls,
user: user.uid
})
})
.catch(err => console.log(err));
Upvotes: 4