Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

114
Views
How do I retrieve a storage downloadURL from inside a firestore collection using RxJS?

I am using Angular 12 with AngularFire / Firebase 9 (Modular). I am struggling with using RxJS to retrieve the downloadURL from storage and adding it to each item of a collection result. Using the following code, I can view the data in the console under "ZoneAwarePromise" but I can not see the data through the template.

const listCollection = collectionData(collection(this.firestore, 'lists'), {idField: 'id'});
this.lists = listCollection.pipe(take(1), map(lists => lists.map(async list => {
  const imgRef = ref(this.storage, list.metaImage);
  const coverImg = await getDownloadURL(imgRef);
  return {...list, coverImg}
})));
about 4 years ago · Juan Pablo Isaza
2 answers
Answer question

0

It's hard to tell for sure from what you've written here but it looks like this.lists is an observable that emits a list of promises. That's what the async keyword does, it's syntactic sugar for creating promises.

You haven't taken/used the values from the promises anywhere (Ie: You're not awaiting them anywhere).

One solution is to rewrite your promises as observables use forkJoin to run your array of observables.

That might look like this:

const listCollection = collectionData(collection(this.firestore, 'lists'), {idField: 'id'});

this.lists = listCollection.pipe(
  take(1), 
  map(lists => lists.map(list => {
    const imgRef = ref(this.storage, list.metaImage);
    return from(getDownloadURL(imgRef)).pipe(
      map(coverImg => ({...list, coverImg}))
    )
  })),
  switchMap(listsCalls => forkJoin(listsCalls))
);
about 4 years ago · Juan Pablo Isaza Report

0

Using a switchMap to combine the results does work; however it causes some render blocking issues in Angular (i.e. Waiting for all "list" items to return getDownloadUrl() before the template can display results). Removing "async" and "await" from the original code and adding an "async" pipe to the Angular template allows data to flow without render blocking.

list.component.ts

const listCollection = collectionData(collection(this.firestore, 'lists'), {idField: 'id'});
this.lists = listCollection.pipe(take(1), map(lists => lists.map(list => {
  const imgRef = ref(this.storage, list.metaImage);
  const coverImg = getDownloadURL(imgRef);
  return {...list, coverImg}
})));

list.component.html

<div class="card" *ngFor="let list of lists | async">
  <div class="card-image">
    <img [src]="list.coverImg | async" />
  </div>
  <h2 class="card-title-lower">
    <a [routerLink]="['/list', list.id]">{{ list.title }}</a>
  </h2>
</div>
about 4 years ago · Juan Pablo Isaza Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!