2016-10-25 12 views
15

W ngOnInit, mój komponent uzyskuje listę użytkowników tak:Jak wymusić odświeżenie w usłudze Obserwowalne w Angular2?

this.userService.getUsers().subscribe(users => { 
    this.users = users; 
}); 

i wdrażania userService.getUsers() wygląda następująco:

getUsers() : Observable<UserModel[]> { 
    return this.http.get('http://localhost:3000/api/user') 
        .map((res: Response) => <UserModel[]>res.json().result) 
        .catch((error: any) => Observable.throw(error.json().error || 'Internal error occurred')); 
} 

Teraz, w innym składnikiem, mam formularz, który może stworzyć nowego użytkownika. Problem polega na tym, że kiedy używam tego drugiego komponentu do utworzenia użytkownika, pierwszy komponent nie wie, że powinien wysłać nowe żądanie GET do backendu, aby odświeżyć swój widok użytkowników. Jak mogę to powiedzieć?

Wiem, że najlepiej byłoby pominąć to dodatkowe żądanie HTTP GET, i po prostu dołączyć dane, które klient już posiada, po tym, jak POST wstawił dane, ale zastanawiam się, jak to będzie w przypadku, gdy nie jest to możliwe z jakiegokolwiek powodu.

Odpowiedz

11

Aby obserwowalna była możliwość podania wartości po zakończeniu wstępnego obserwowania Http, można go podać w temacie RxJS. Ponieważ zachowanie buforowania jest pożądane, pasuje do przypadku.

To powinno być coś jak

class UserService { 
    private usersSubject: Subject; 
    private usersRequest: Observable; 

    constructor(private http: Http) { 
    this.usersSubject = new ReplaySubject(1); 
    } 

    getUsers(refresh: boolean = false) { 
    if (refresh || !this.usersRequest) { 
     this.usersRequest = this.http.get(...).map(res => res.json().result); 

     this.usersRequest.subscribe(
     result => this.usersSubject.next(result), 
     err => this.usersSubject.error(err) 
    ); 
    } 

    return this.usersSubject.asObservable(); 
    } 
} 

Ponieważ istnieje już obiekt, nowy użytkownik może zostać wciśnięty bez aktualizacji wykazu z serwera:

this.getUsers().take(1).subscribe(users => 
    this.usersSubject.next([...users, newUser]) 
) 
+0

Mnóstwo świetnych odpowiedzi tutaj. Poszedłem z podejściem, które zaproponowałeś i działa świetnie. – Josh1billion

+0

Fajnie, cieszę się, że to działa dla ciebie. – estus

+0

jak się wypisać przy użyciu tej metody? –

3

Sposób, w jaki radziłem sobie z tym problemem, polegał na korzystaniu z pośrednika. this.userService.getUsers() zwraca wartość Rx.BehviorSubject, która jest inicjowana po zwrocie obserwowalnego http.

coś blisko tego:

getUsers() : BehaviorSubjec<UserModel[]> { 
    return this.behaviorSubject; 
} 
updateUsers() { 
    this.http.get('http://localhost:3000/api/user') 
        .map((res: Response) => <UserModel[]>res.json().result) 
        .catch((error: any) => Observable.throw(error.json().error || 'Internal error occurred')) 
        .subscribe((value) => { 
         this.behaviorSubject.onNext(value)}); 
} 
2

Być może wyglądać na użyciu realizację Redux takich jak ngrx/sklepu, to sprawia, że ​​zarządzanie stan między komponentami naprawdę proste i predicatable. Po prostu prześlij nowego użytkownika do sklepu, a zostanie on rozpropagowany do wszystkich składników, które mają odniesienie do obserwowalnych sklepów.

ngrx/store

Jeśli po więcej kodzie komponentu mogę edytować to na przykład pracy.

Powiązane problemy