Angular - как получить состояние из ngrx и затем выполнить http - PullRequest
0 голосов
/ 15 января 2019

У меня есть метод в службе, где мне нужно получить некоторые данные из хранилища и использовать их в запросе http, но я продолжаю получать ошибки или запрос http не выполняется, вот что я пытаюсь:

class SettingService {
 updateSettings({ settings }) {
  return this.store.select(s => s.settings).map((state: any) => {
    const { id } = state.data;

    return this.http.put('route/' + id, { settings }).pipe(map((response: any) => {
      const { data } = response;
      this.store.dispatch(new GetSettingsSuccess({ data }));
      return data;
    })).pipe(catchError(this.errorHandlerService.handleError));
  });
 }
}

Ошибки, которые я получаю, такие как

Свойство 'map' не существует для типа 'Observable'

Я использую это для импорта службы в компонент, затем:

this.settingService.updateSettings({ settings }).subscribe();

метод вызывается, но по какой-то причине http-запрос не происходит. Я тоже должен подписаться на http запрос? или я должен использовать pipe вместо map и назначить вместо него несколько операторов?

Ответы [ 3 ]

0 голосов
/ 15 января 2019

Вот псевдокод того, что вы можете попробовать:

 updateSettings({ settings }) {
   // use store select through a reducer:
    return this.store.select('your_reducer_here').subscribe( state => {
      //get id from your state  
      const id = state.data;

      //use that id in your http call
      return this.http.put('route/' + id, { settings }).pipe(map((response: any) => {
        const { data } = response;
        this.store.dispatch(new GetSettingsSuccess({ data }));
        return data;
      })).pipe(catchError(this.errorHandlerService.handleError));
    });
    })
}
0 голосов
/ 15 января 2019

Вы должны объединить несколько операторов в pipe. Используйте switchMap (или даже mergeMap), чтобы отобразить вывод вашего магазина в Observable из запроса Http, а затем выполнять другие свои задачи, каждый в своем собственном операторе. Таким образом вы получите намного более чистый код.

Это должно выглядеть примерно так:

updateSettings({ settings }) {
  return this.store.select(s => s.settings)
    .pipe(
      // map the state from your store to the http request
      switchMap((state: any) => this.http.put('route/' + state.data.id, { settings })),
      // map the http response to the data your care about
      map((response: any) => response.data),
      // execute any other task with that data
      tap(data => this.store.dispatch(new GetSettingsSuccess({ data }))),
      // catch errors if they occurr
      catchError(this.errorHandlerService.handleError),   
    );

Затем вы подписываетесь на возвращаемую Observable, и ваш http-запрос будет выполнен после того, как значение из хранилища будет отправлено.

this.settingService.updateSettings({ settings }).subscribe(
  // you'll have access to your data from the http response here
  data => doSomething(data) 
);
0 голосов
/ 15 января 2019

Вы называете карту на наблюдаемой здесь this.store.select(s => s.settings).map((state: any) Вам необходимо использовать pipe(map()). В этой строке вы все делаете правильно: return this.http.put('route/' + id, { settings }).pipe(map((response: any)

...