【发布时间】:2020-06-23 20:19:39
【问题描述】:
我想创建一个服务方法,它在第一次执行时将从 URL 获取数据集,缓存数据集,然后与随后调用服务方法的组件共享数据集的同一实例。
我已经开始创建两个解决方案。这两种解决方案的问题在于,在加载 Angular 应用程序后的最初几毫秒内,它们会多次从 URL 获取数据集,和/或它们会向控制台抛出一些错误消息,但在两个组件之间的第一次或第二次导航之后,数据似乎已正确共享,并且没有更多的 URL 往返。
方法#1
import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { Observable, of } from 'rxjs';
@Injectable({
providedIn: 'root',
})
export class FirstService {
private url = 'http://somedummydomain.com/api/entries';
private data: any;
private observable: Observable<any>;
constructor(private http: HttpClient) {}
getData() : Observable<any> {
if (this.data) {
return of(this.data);
} else if (this.observable) {
return this.observable;
} else {
this.observable = this.http.get(this.url);
this.observable.subscribe((data) => {
this.data = data;
this.observable = null;
});
return this.observable;
}
}
}
方法 #2
import { Injectable } from '@angular/core';
import { BehaviorSubject, Observable } from 'rxjs';
import { HttpClient } from '@angular/common/http';
@Injectable({
providedIn: 'root',
})
export class SecondService {
private sharedData: BehaviorSubject<any> = new BehaviorSubject<any>(null);
private url = 'http://somedummydomain.com/api/entries';
constructor(private http: HttpClient) {
this.http.get(this.url).subscribe((data) => {
this.addData(data);
});
}
private addData(data: any) {
this.sharedData.next(data);
}
getData(): Observable<any> {
return this.sharedData.asObservable();
}
}
Lib 版本
- 角度:v9.1.9
- rxjs: v6.5.5
谢谢!
【问题讨论】:
-
基本上没有理由为什么要多次进行HTTP调用...您能否将
console.log放在SecondService的构造函数中并验证它只调用一次? -
是的,谢谢。我实际上在 HTML 文件中有一个错误,导致控制台错误消息。但如果我能让第一种方法工作,我仍然会很感激,因为我稍后需要将 ReloadFromUrl 和 SaveDataToUrl 功能添加到服务中,第一种方法对我来说似乎不那么模糊,因为它明确包含“数据”属性。
-
方法 1 中的
data是方法 2 中的sharedData.value。我会继续方法 2,因为它包含的逻辑更少。但是,这样做的“反应性”方式不是两者之一。但我怀疑“反应式”方法会更加“晦涩”;-)
标签: angular typescript rxjs observable angular-services