0

I am trying to Learn Async Pipe and how to use them. however I have an issue with using Async Pipe in the following case;

I am using this fake/dummy API Cat API I can't figure how to retrieve the Object Data inside the observable value.

TS Code

import { Component, OnInit } from '@angular/core';
import { HttpService } from '../services/http/http.service';
import { facts } from '../interfaces/facts';
import { Observable } from 'rxjs';
@Component({
  selector: 'app-home',
  templateUrl: './home.component.html',
  styleUrls: ['./home.component.scss']
})
export class HomeComponent implements OnInit{
  facts$! : Observable<facts[]>
  constructor(private client : HttpService){

  }
  ngOnInit(): void {

    this.facts$ = this.client.getListFacts(25, 5)
  }

}

Interface

export interface facts {
  fact : string,
  length : number
}

HTML

<div class='home'>
  <ul style="margin: 0 0 0 0">
    <li *ngFor="let fact of (facts$ | async)">{{fact.fact}}</li>
  </ul>
</div>

HTTP Service

  getListFacts(length : number, limit : number) : Observable<facts[]>{
    return this.client.get<facts[]>(`https://catfact.ninja/facts?max_length=${length}&limit=${limit}`)

I have tried to async pipe results, fact of facts list inside the HTML code, however it renders nothing

1 Answer 1

3

Your typing of the API response is wrong. What comes from the API is an object with several properties related to pagination, and data array, which is what you're after. One way to consume it would be

getListFacts(length: number, limit: number) : Observable<facts[]> {
    return this.client
        .get<{ data: facts[] }>(`https://catfact.ninja/factsmax_length=${length}&limit=${limit}`)
        .pipe(map(({ data }) => data));
}

(Also, the interface should be named Fact, not facts: singular, because it represents a single entry, and uppercase, because that's the convention for types/interfaces/classes).

Sign up to request clarification or add additional context in comments.

4 Comments

@MamdouhMorad Please accept the answer when it solved your problem
Hey, Sorry for asking again, but I am confused; I am now trying different API dog.ceo/dog-api Which I have defined an Interface for ` ` ` export interface Random{ message : string, status : string } ` ` ` and my http request is like this ` ` ` getRandomImage(): Observable<Random> { return this.client.get<Random>(https://dog.ceo/api/breeds/image/random) } ` ` ` HTML ` ` ` <div> <p *ngIf=" random$ | async">{{ random$.status }}</p> </div> ` ` `
For what I understand, API returns an Object with message and status keys with value types string. Why is this observable I defined failing to render ? also Sorry, I am new here. I don't know how to accept as an answer
property 'status' does not exist on type 'Observable<Random>'

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.