Angular HttpClient: получить данные со страниц API RESTfull (цикл следующей страницы) - PullRequest
0 голосов
/ 12 сентября 2018

У кого-нибудь есть хороший пример или учебное пособие, где я могу найти полезные методы для извлечения данных из разбитого на страницы API RESTfull, используя Angular 6 с HttpClient?

Получение данных из рассматриваемого API. В моем файле service.ts используется следующий код:

getApiData(term: string): Observable<ApiResponse[]> {
  let apiUri = this.baseUrl;
  let msg = 'data fetched from API';

  if (term.trim()) {
    apiUri = this.baseUrl + this.queryUrl + term;
    msg = msg + ' matching: ' + term;
  }
  return this.http.get<ApiResponse[]>(apiUri)
    .pipe(
      tap(data => {
        this.log(msg);
      }),
      catchError(this.handleError('getApiData', []))
    );
}

Однако я не могу найти подсказки, как перебрать все страницы (data ['next']) конечной точки API с использованием наблюдаемых ограничений.

Буду признателен за каждую идею или ссылку на дополнительную информацию для решения этой распространенной проблемы. Очевидно, что у меня также нет правильных терминов, поэтому найдите подходящий ответ здесь. : - /

1 Ответ

0 голосов
/ 12 сентября 2018

Прежде всего, будьте осторожны с .trim() для переменной, которая может быть неопределенной. Я бы изменил ваш

if (term.trim()) { ... }

с

if (term && term.trim()) { ... }

Что касается итерации данных, полученных из наблюдаемой, я бы сделал следующее. Предположим, что ваша функция getApiData принадлежит услуге my-backend.service.ts. Предположим, что вы хотите вызвать компонент, который был в вашем коде. Если ваш сервис добавлен в ваш app.modules, вы можете добавить его в свой компонент из конструктора следующим образом: сначала импортируйте его:

import {MyBackend} from "/.myBackend.service";

затем добавьте его в конструктор (введите его) и глобальную переменную для ваших данных:

data:any;
constructor( public myBackend: MyBackend){}

Теперь, где бы вы ни хотели использовать свой сервис, вы делаете следующее:

this.myBackend.getApiData(term).subscribe( (data) => {
this.data = data;
});

И ваши данные будут храниться в вашем компоненте. Теперь вы можете выполнить итерацию или сделать все необходимое (например, data ["next"]).

Дайте мне знать, если мне неясно или вам нужна более подробная информация.

EDIT

Если вы имеете дело с постраничным поиском, ваш this.data должен иметь информацию о количестве страниц или количестве найденных результатов в зависимости от количества отображаемых результатов. В этом случае вам нужно будет решить, что делать, если вам придется искать снова и вызывать службу несколько раз (или информировать пользователя).

В этом случае я считаю, что не имеет смысла повторять вызовы к http.get в вашем сервисе, постраничный поиск не предназначен для такой работы, скорее логичным вариантом было бы показывать результаты страницу за страницей пользователю .

Если, тем не менее, вы хотите сделать что-то подобное (автоматически выполнять поиск по вашему компоненту). Вы можете реализовать такую ​​функцию в своем компоненте:

async retrieveAllPages(searchInput){
 let finish = false;
 dataPages = [];

 while (!finish){
  const page = wait this.myBackend.getApiData(searchInput).toPromise()
  dataPages.push(page);
  finish = this.decideIfSearchIsFinished(page);
  searchInput = this.updateSearchTermNextPage (searchInput);
 }
}

Вам также понадобятся эти функции. Я не указываю их, потому что я не знаю, как работает ваш бэкэнд API:

decideIfSearchIsFinished(page):boolean{
//looks into the page object response to see if there are more pages or if we are in the last one
//..
}

updateSearchTermNextPage(term):string{
//updates the search term to search for a new page
}
...