Я пытаюсь получить данные через REST с помощью angular 2 HttpClient. Я следую руководству по angular здесь https://angular.io/tutorial/toh-pt6 а в разделе Герои и HTTP вы увидите этот фрагмент кода, который используется для получения данных о героях через http.
getHeroes(): Promise<Hero[]> {
return this.http.get(this.heroesUrl)
.toPromise()
.then(response => response.json().data as Hero[])
.catch(this.handleError);
}
А ниже аналогичная версия, которую я написал в своем приложении.
fetch(startIndex: number, limit: number): Promise<Order[]> {
let url = this.baseUrl + "&startIndex=" + startIndex + "&limit=" + limit;
return this.http.get(url)
.toPromise()
.then(response => response.json().results as Order[])
.catch(this.handleError);
}
Я использую InteliJ Idea, и на вызове response.json () есть красная линия, и даже когда я пытаюсь выполнить сборку с помощью ng build, я получаю сообщение об ошибке.
Свойство json не существует для типа Object.
Вы можете заметить, что вместо json().data
у меня json().results
. Это потому, что согласно руководству сервер ответил объектом с полем data
, но мой собственный сервер отвечает объектом с полем results
. Если вы немного прокрутите руководство, вы увидите этот момент.
Обратите внимание на форму данных, которые возвращает сервер. Этот конкретный пример веб-API в памяти возвращает объект со свойством данных. Ваш API может вернуть что-то еще. Настройте код в соответствии с вашим веб-API.
Пытаясь исправить это, я попробовал что-то вроде этого
(response: Response) => response.json().results as Order[]
Когда я это сделал, метод .json () был разрешен, но появилась другая ошибка,
Результаты свойства не существуют для типа Promise
Я попытался исправить это, определив интерфейс
interface OrderResponse {
orders: Order[];
}
И изменил вызов get на
.get<OrderResponse>(url)...
Но это тоже не сработало. Выскочила еще одна ошибка
Тип «OrderResponse» нельзя присвоить типу «Response».
Следует отметить, что в учебнике они использовали Angular HttpModule, но в моем приложении я использую новый Angular HttpClientModule, так что, возможно, именно здесь возникает ошибка.
Я новичок в Angular 2, и это первое приложение, которое я создаю с его помощью. Если приведенный выше код больше недействителен с новым HttpClientModule, я был бы признателен за любую помощь в том, как достичь того же с новым HttpClientModule.
Я нашел похожие вопросы Свойство 'json' не существует для типа '{} ' и Свойство не существует для типа «объект» Но ни один из ответов мне не помог.
Обновить
Как следует из комментариев, в новом HttpClientModule нет метода .json (). Я все еще признателен за помощь в том, как добиться того же эффекта с новым модулем. Из гайда сделали что-то вроде этого
http.get<ItemsResponse>('/api/items').subscribe(data => {
// data is now an instance of type ItemsResponse, so you can do this:
this.results = data.results;
});
Что я прекрасно понимаю, но моя проблема в том, что этот код находится не в компоненте, а в службе, поэтому вызов подписки и присвоение результата полю экземпляра не имеет большого смысла.
Мне нужна моя служба для возврата массива заказов, заключенных в обещание. Мои компоненты могут просто звонить, например
this.orderService.fetch(0, 10).then(orders => this.orders = orders)
Я также подумал об объявлении локальной переменной в моем методе выборки службы, чтобы я мог
.subscribe(data => {
this.orders = data.results;
}
// and out of the get call I return my local variable orders like
return Promise.resolve(orders)
Но для меня это не имеет большого смысла, поскольку вызов .get () является асинхронным, и метод может возвращаться даже до того, как будут получены все данные, а массив заказов может быть пустым.
Обновить
В соответствии с просьбой вот код для handleError
private handleError(error: any): Promise<any> {
console.log('An error occured ', error);
return Promise.reject(error.message || error);
}