1
votes

My understanding of the Angular async pipe is that is subscribes to an exposed Observable for you in the HTML template. E.G

Component

export class TestComponent {
    let todos$: Observable<Array<Todo>>;

    constructor(private http: HttpClient) {}

    ngOnInit() {
        this.todos$ = this.http.get<Array<Todos>>(...)
    }
}

Template

<div *ngFor="let todo of todos$ | async">
    {{ todo }}
</div>

My understanding is that the HttpClient Observable will emit the following events for success:

next(value)
completed

and on error

error(error)
completed

When an observable emits a completed event, the subscription is closed.

Therefore, if you are subscribed to a cold observable like Angulars HttpClient Observable, how do you retry that HttpClient request?

The async operator does the initial subscription but will be closed as soon as the cold observable completes, how do you get the async operator to resubscribe if you want to execute it again? for example if you wanted to do a refresh of the data.

2
What triggers the new request? - Kurt Hamilton
You could have a refresh button for example. If I understand it correctly, the async operator would need to subscribe again to the httpclient cold observable. - Fergal Rooney

2 Answers

3
votes

just reassign the todos$ this will trigger the http request again

component

export class TestComponent {
    public todos$: Observable<Array<Todo>>;

    constructor(private http: HttpClient) {}

    ngOnInit() {
     this.getTodos();
    }

    getTodos(){
        this.todos$ = this.http.get<Array<Todos>>(...);
    }
}

template

<button (click)="getTodos()" >Refresh 🚀</button>

demo 🚀

1
votes

You have a retry and retryWhen operators. Play with them :)

https://rxjs-dev.firebaseapp.com/api/operators/retry

https://rxjs-dev.firebaseapp.com/api/operators/retryWhen

@edit

To refresh the data on success you can do it like this:


export class TestComponent {
    refresh$ = new BehaviorSubject(true);
    todos$: Observable<Array<Todo>>;

    constructor(private http: HttpClient) {}

    ngOnInit() {
        this.todos$ = this.refresh$
            .pipe(
                 switchMap(() => this.http.get<Array<Todos>>(...))
            )
    }

    refreshData() {
        this.refresh$.next();
    }
}