#angular #rxjs
Вопрос:
Я узнаю об архитектуре на основе Push с помощью RxJS и Angular.
Из того, что я узнал, я понял, что архитектуры на основе вытягивания-это когда представление вызывает для получения данных.
Это может быть использование общих объектов или по назначению:
users$ = this.facade.users$
loadUser() { this.facade.loadUser(); }
На фасаде:
users$ = new BeahviorSubject();
loadUser() { this.http.get('...').subscribe(users => { this.users$.next(users); }) }
В Push-базе он должен реагировать на такие изменения, как:
search = new FormControl();
search.valueChanges().pipe(tap(searchTerm => searchSomething(searchTerm)));
Это хорошо, когда дело доходит до событий. но что, если мне нужно «отреагировать», чтобы нажать на кнопку?
В основном кнопка сохранения «вытягивает» данные. Поэтому я в замешательстве по этому поводу, и будет полезно, если кто-нибудь сможет разрешить этот конфликт.
Ответ №1:
В то время как компонент все еще запускает событие «push» при нажатии кнопки, эффект события может произойти реактивно.
Используя пример очень простой поисковой формы…
Служебный файл
private searchTerm = new Subject<string>();
public searchResult$ = this.searchTerm.pipe(
switchMap(searchTerm =>
this.http.get<string[]>(`url?${searchTerm}`)
),
startWith([])
);
public newSearchTerm = (newTerm:string) => {
this.searchTerm.next(newTerm);
}
Мы объявляем частную тему, которая будет выдавать наш поисковый запрос.
Затем мы объявляем наблюдаемое, которое примет отправленный поисковый запрос, и подключим его к нашему HTTP-запросу. Мы можем вернуть http-запрос, так как он возвращает наблюдаемый ответ.
Поскольку searchTerm
субъект в начале ничего не выдает, мы добавляем наше начальное значение (пустой массив) с помощью оператора startWith()
.
Наконец, мы создаем общедоступный метод, который позволяет другим классам выдавать следующий поисковый запрос.
Файл TS компонента
public searchInput = new FormControl('');
public searchResult$ = this.service.searchResult$;
public searchEvent = () => {
this.service.newSearchTerm(searchInput.value);
}
Мы объявляем наш поисковый ввод FormControl, как вы сделали в своем примере.
Затем мы подписываемся на searchResult$
наблюдаемое из нашего сервиса. Опять же, это зависит от того, что субъект службы выдаст поисковый запрос.
Наконец, мы создаем метод для обработки события нажатия кнопки. В то время как метод возвращает значение void, он вызовет метод службы для выдачи нового поискового запроса.
Это приведет к тому, что состояние нашего компонента searchResult$
отреагирует, отобразив значение, возвращенное из HTTP-запроса службы.
HTML-файл компонента
<input formControlName="searchInput" />
<button (click)="searchEvent()">Search</button>
<ul>
<li *ngFor="let result of searchResult$ | async">{{ result }}</li>
</ul>
Наконец, мы настраиваем наш HTML. Вывод кнопки вызовет searchEvent()
метод. И мы используем async
трубу, чтобы подписаться на searchResult$
нее . Это помещает всю наблюдаемую цепочку в одну единственную подписку в этом представлении. Когда компонент будет уничтожен (изменение на экране), это приведет к отмене подписки всей наблюдаемой цепочки.