1

I have a resolver which uses the url to fetch the parent called a bubble, for the reply that I then want to fetch based on the URL.

Problem is that my findReplyByUrl() function wont wait for the DOCID that I am trying to resolve. The resolver delivers a null observable to the component.

Does anyone know where I am going wrong here?

reply.resolver.ts

@Injectable({
    providedIn: "root"
})
export class ReplyResolver implements Resolve<Promise<Observable<Reply>>> {

    constructor(private replyModeStore: ReplyModeStore,
                private bubbleStore: BubbleStore,
                protected bubbleResolver: BubbleResolver) {

    }

    async resolve(route: ActivatedRouteSnapshot, 
            state: RouterStateSnapshot): Promise<Observable<Reply>> {
            
            const replyUrl = route.paramMap.get("replyUrl");

            const bubbleUrl = replyUrl.split("-reply-")[0];
            console.log(bubbleUrl) //It works here 
            let bubbleDocId = await this.returnBubble(bubbleUrl);
            console.log(bubbleDocId) // this is undefined
            const reply = await this.replyModeStore.findReplyByUrl(await bubbleDocId, replyUrl)     

            return await reply;
    }

    async returnBubble(bubbleUrl:string):Promise<string> {
        let bubbleUId:string;
        const bubble$ = this.bubbleStore.findBubbleByUrl(bubbleUrl);
        
        await bubble$.subscribe(res => {
            bubbleUId = res.docid
        });

        return await bubbleUId;

    }
}

reply.store.ts

    async findReplyByUrl(bubbleDocId:string, replyUrl:string):Promise<Observable<Reply>>{

        return from(this.db.collection(`vwubbles/${bubbleDocId}/replies`,
            ref => ref.where("url", "==", replyUrl))
            .get()
            .pipe(
                map(results => {

                    const replies = convertSnaps<Reply>(results);

                    return replies.length == 1 ? replies[0] : null;
                    // this.individualReplySubject.next(replyToSet);

                })
            )
        )
    }

bubbles-routing.module.ts

const routes: Routes = [
  {
    path: "",
    component: VwubblesComponent
  },
  {
    path: 'bubble/:bubbleUrl',
    component: BubbleComponent,
    resolve: {
      bubble: BubbleResolver
    }
  },
    {
      path: "reply/:replyUrl",
      component: ReplyComponent,
      resolve: {
        reply: ReplyResolver
      }
    }
];

@NgModule({
  imports: [
    RouterModule.forChild(routes)
  ],
  exports: [RouterModule],
  providers: [
    ReplyResolver,
    BubbleResolver
  ]
})
export class BubblesRoutingModule {}
Matthieu Riegler
  • 31,918
  • 20
  • 95
  • 134
nuccio
  • 316
  • 6
  • 17

1 Answers1

3

Your problem is with returnBubble which doesn't return a Promise resolving your request.

returnBubble(bubbleUrl: string): Promise<string> {
    return firstValueFrom(
        this.bubbleStore.findBubbleByUrl(bubbleUrl).pipe(map((res) => res.docid))
    );
}·
Matthieu Riegler
  • 31,918
  • 20
  • 95
  • 134
  • Thanks, I had to upgrade to rxjs 7 to fix this issue, it took me some time, but it was worth it. I used something very similar to what you provided so I gave you the answer. Thanks a bunch! – nuccio Nov 10 '22 at 03:44
  • 1
    Oh yeah, the solution for rxjs 6 would be `toPromise()` instead of `firstValueFrom()` – Matthieu Riegler Nov 10 '22 at 08:45