有没有办法在使用可观察对象时将复杂的 json 数据映射到打字稿中的接口?
Is there a way to map complex json data onto interfaces in typescript while using observables?
我正在尝试制作简单的网络新闻 reader,主要基于 google 新闻 api (https://newsapi.org/s/google-news-api)。我已经像往常一样完成了所有服务、模型等工作,但我在将数据映射到具体接口时遇到了问题。 Google api returns 在端点之一 ('top-headlines') 上,数据格式如下:
{
"status": "ok",
"totalResults": 38,
"articles": [
{
"source": {
"id": "the-new-york-times",
"name": "The New York Times"
},
"author": null,
"title": "Hong Kong Protesters Clash with Police Amid Fears of Mob
Violence - The New York Times",
"description": "some description",
"url": "https://www.nytimes.com/2019/08/11/world/asia/hong-kong-
protest.html",
"urlToImage":
"https://static01.nyt.com/images/2019/08/11/world/11hongkong15/
11hongkong15-facebookJumbo.jpg",
"publishedAt": "2019-08-11T11:19:03Z",
"content": "some content… [+751 chars]"
},
(...and many many more articles)
]
}
我只需要文章。我知道如果我从 api 中获取这些数据,我可以调用 myvariablename.articles,但这对我来说似乎不正确。
我首先尝试使用 rxjs 映射方法进行映射。但是我在控制台中收到错误消息,指出 Articles 模型中没有 属性 篇文章。所以我在响应模型(接口)中准备了响应模型和嵌套文章 属性。我得到了完全相同的错误。我在想,也许在方法 Observable 中定义有一些问题,所以我切换到 Response 但没有运气,现在我正在订阅和使用服务方法的组件出现错误,它说: "Type Response[] is not assignable to type Article[]"
top-news.service.ts
(...all imports)
export class TopNewsService {
(... ommited defining of variables like url etc.)
public getAll(): Observable<Response[]> {
return this.httpClient
.get<Response[]>(`${this.url}/${this.endpoint}?country=us&apiKey=${this.token}`)
.pipe(
map(response => response.articles),
catchError(this.handleError)
);
}
(...error handling)
}
article.ts
export interface Article {
source: {
id: string;
name: string;
};
author: string;
title: string;
description: string;
url: string;
urlToImage: string;
publishedAt: string;
content: string;
}
response.ts
import { Article } from './article';
export interface Response {
status: string;
totalResults: number;
articles: Article;
}
头条新闻-component.ts
(...all imports)
export class TopNewsComponent implements OnInit {
articles: Article[];
constructor(private http: HttpClient, private topNewsService: TopNewsService) { }
ngOnInit() {
this.getAllProjects();
}
getAllProjects() {
this.topNewsService.getAll().subscribe(data => {
this.articles = data;
console.log(this.articles)
},
(err: string) => {
alert(err);
});
}
}
我希望能够在服务中映射数据,return 仅在文章中映射数据,然后(如果可能的话)在我的组件中获取这些数据并将其分配给定义类型为 Article[] 的已创建变量.
您正在使用
this.httpClient.get<Response[]>
这意味着你期望Google到return一个响应数组。但这不是 return 的意思。它 return 是一个 单 Response
。所以应该是
this.httpClient.get<Response>
并且由于您(尝试)将此响应映射到一系列文章,因此可以观察到您的服务 returns 是 Observable<Article[]>
,而不是 Observable<Response[]>
。所以应该是
public getAll(): Observable<Article[]> {
这个界面
export interface Response {
status: string;
totalResults: number;
articles: Article;
}
也是错误的。回复不包含一篇文章。它包含一系列文章。看看 JSON:
{
"status": "ok", // one status string
"totalResults": 38, // one totalResults number
"articles": [ // an **array** of articles
..
]
}
所以应该是
export interface Response {
status: string;
totalResults: number;
articles: Article[];
}
我正在尝试制作简单的网络新闻 reader,主要基于 google 新闻 api (https://newsapi.org/s/google-news-api)。我已经像往常一样完成了所有服务、模型等工作,但我在将数据映射到具体接口时遇到了问题。 Google api returns 在端点之一 ('top-headlines') 上,数据格式如下:
{
"status": "ok",
"totalResults": 38,
"articles": [
{
"source": {
"id": "the-new-york-times",
"name": "The New York Times"
},
"author": null,
"title": "Hong Kong Protesters Clash with Police Amid Fears of Mob
Violence - The New York Times",
"description": "some description",
"url": "https://www.nytimes.com/2019/08/11/world/asia/hong-kong-
protest.html",
"urlToImage":
"https://static01.nyt.com/images/2019/08/11/world/11hongkong15/
11hongkong15-facebookJumbo.jpg",
"publishedAt": "2019-08-11T11:19:03Z",
"content": "some content… [+751 chars]"
},
(...and many many more articles)
]
}
我只需要文章。我知道如果我从 api 中获取这些数据,我可以调用 myvariablename.articles,但这对我来说似乎不正确。
我首先尝试使用 rxjs 映射方法进行映射。但是我在控制台中收到错误消息,指出 Articles 模型中没有 属性 篇文章。所以我在响应模型(接口)中准备了响应模型和嵌套文章 属性。我得到了完全相同的错误。我在想,也许在方法 Observable 中定义有一些问题,所以我切换到 Response 但没有运气,现在我正在订阅和使用服务方法的组件出现错误,它说: "Type Response[] is not assignable to type Article[]"
top-news.service.ts
(...all imports)
export class TopNewsService {
(... ommited defining of variables like url etc.)
public getAll(): Observable<Response[]> {
return this.httpClient
.get<Response[]>(`${this.url}/${this.endpoint}?country=us&apiKey=${this.token}`)
.pipe(
map(response => response.articles),
catchError(this.handleError)
);
}
(...error handling)
}
article.ts
export interface Article {
source: {
id: string;
name: string;
};
author: string;
title: string;
description: string;
url: string;
urlToImage: string;
publishedAt: string;
content: string;
}
response.ts
import { Article } from './article';
export interface Response {
status: string;
totalResults: number;
articles: Article;
}
头条新闻-component.ts
(...all imports)
export class TopNewsComponent implements OnInit {
articles: Article[];
constructor(private http: HttpClient, private topNewsService: TopNewsService) { }
ngOnInit() {
this.getAllProjects();
}
getAllProjects() {
this.topNewsService.getAll().subscribe(data => {
this.articles = data;
console.log(this.articles)
},
(err: string) => {
alert(err);
});
}
}
我希望能够在服务中映射数据,return 仅在文章中映射数据,然后(如果可能的话)在我的组件中获取这些数据并将其分配给定义类型为 Article[] 的已创建变量.
您正在使用
this.httpClient.get<Response[]>
这意味着你期望Google到return一个响应数组。但这不是 return 的意思。它 return 是一个 单 Response
。所以应该是
this.httpClient.get<Response>
并且由于您(尝试)将此响应映射到一系列文章,因此可以观察到您的服务 returns 是 Observable<Article[]>
,而不是 Observable<Response[]>
。所以应该是
public getAll(): Observable<Article[]> {
这个界面
export interface Response {
status: string;
totalResults: number;
articles: Article;
}
也是错误的。回复不包含一篇文章。它包含一系列文章。看看 JSON:
{
"status": "ok", // one status string
"totalResults": 38, // one totalResults number
"articles": [ // an **array** of articles
..
]
}
所以应该是
export interface Response {
status: string;
totalResults: number;
articles: Article[];
}