我尝试使用 rxResource 显示数据。但是,返回的数据始终未定义。然而,检查网络选项卡显示数据确实正在获取,只是我的组件出了点问题。这段代码有什么问题?因为我似乎找不到问题所在。
API 服务
import { HttpClient } from '@angular/common/http';
import { inject, Injectable } from '@angular/core';
import { httpResource } from "@angular/common/http";
@Injectable({
providedIn: 'root'
})
export class ApiService {
private readonly httpClient = inject(HttpClient);
public GET<T>(path: string, options?: any) {
return this.httpClient.get<T>(path, options);
}
组件文件:
import { Component, inject, signal } from '@angular/core';
import { ApiService } from '@services/api.service';
import { rxResource, toSignal } from '@angular/core/rxjs-interop';
import { distinctUntilChanged, map } from 'rxjs';
@Component({
selector: 'app-blogs',
templateUrl: './blogs.component.html',
styleUrl: './blogs.component.scss'
})
export class BlogsComponent {
apiService = inject(ApiService)
query = signal('')
rxBlog = rxResource({
request: () => this.query(),
loader: () =>
this.apiService.GET(`https://api.nationalize.io/?name=${this.query()}`)
.pipe(
distinctUntilChanged(),
map((blogs) => blogs),
)
})
search(event: Event) {
const { value } = event.target as HTMLInputElement;
this.query.set(value);
}
}
// Template
<p>blogs works!</p>
<input (input)="search($event)" placeholder="Search user..."/>
<br />
<ul>
@let error = rxBlog.error();
@if (error) {
<p>{{ error }}</p>
}
@if (rxBlog.isLoading()) {
<p>Loading Blogs...</p>
}
@for (blog of (rxBlog.value()).country) {
{{blog.country_id}}
}
</ul>
Json数据如下:
{
"count": 22997,
"name": "steve",
"country": [
{
"country_id": "KE",
"probability": 0.0728971981962264
},
]
}
初始点:
当您想要
debounce
使用输入或额外的反应操作时rxjs
,这rxResource
是最好的选择。当您只想进行 API 调用并具有反应性时,这
httpResource
是最佳选择。由于
httpResource
引擎盖下有呼叫HttpClient
,因此不需要服务。其优点
httpResource
是可以大量减少样板代码,用于进行简单的 API 调用。使用HttpResource:
您有一个非常基本的获取示例,因此
rxResource
不是最合适的,而是选择httpResource
,我们只需要在回调中提供一个url
,当回调中的源信号发生变化时,它将被动地获取数据。完整代码:
Stackblitz 演示
使用 RxResource:
直到源信号发生变化时才会
rxResource
触发 API,因此无需distinctUntilChanged
。它还会在初始化期间获取一次值。下面是一个演示 rxResource 实际作用的示例:
Stackblitz 演示
附加要点:
为获取的数据定义一个接口总是好的。
获取的属性有可能
country
是undefined
,因此我使用let
与或运算符||
来提供默认值(如果是)undefined
。