import { Injectable } from '@angular/core';
import { HttpClient, HttpErrorResponse } from '@angular/common/http';
import { Observable } from 'rxjs';
import { catchError } from 'rxjs/operators';
@Injectable()
export class ApiService {
constructor(private http: HttpClient) { }
// get API request
public apiGetRequest(url: any): Observable<any> {
return this.http.get(url)
.pipe(
catchError(this.handleError('apiGetRequest'))
);
}
}
我在rxjs 5.5.6版中使用了angular 5,我试图缓存多个http get请求。
答案 0 :(得分:1)
这样就没有rxjs
♂️,但是您可以检查此answer
@Injectable()
export class CashingService {
private __cach = {}
isCashed(url: string) {
return this.__cach[url];
}
getData(url: string) {
return this.__cach[url]
}
setData(url) {
return (data) => {
if (data && (data instanceof Error) === false)
this.__cach[url] = data
};
}
reset() {
this.__cach = {};
}
}
注入缓存服务
@Injectable()
export class ApiService {
constructor(private http: HttpClient , private _c:CachingService ) { }
// get API request
public apiGetRequest(url: any): Observable<any> {
if (this._c.isCashed(url)){
return of(this._c.getData(url));
} else {
return this.http.get(url)
.pipe(
tab(this._c.setData(url)),
catchError(this.handleError('apiGetRequest'))
);
}
}
}
答案 1 :(得分:1)
正确的方法如下:
private varName$: Observable<T>;
private _apiGetRequest():Observable<T>{
return this.http.get('endpoint');
}
public apiGetRequest():Observable<T>{
if(!this.varName$){
this.varName$ = this._apiGetRequest().pipe(shareReplay(1));
}
return this.varName$
}
这样,私有观察者将保留最后发出的值
答案 2 :(得分:1)
这是我正在使用的缓存服务,它将数据存储在Redux存储中,但是很容易更改为所需的任何数据持有人。
@Injectable()
export class CacheManager {
constructor(
private store: NgRedux<IAppState>,
private actions: GlobalActions) {
}
public get<T>(key: CacheKey, thisArg: any, dataRetriver: (...args: any[]) => T | Observable<T>, ...args: any[]): Observable<T> {
if (this.isCached(key)) {
return of(this.getFromCache<T>(key));
}
const data$: T | Observable<T> = dataRetriver.apply(thisArg, args);
if (data$ instanceof Observable) {
return data$.pipe(
tap(result => this.addToCache(key, result))
);
}
else {
this.addToCache(key, data$);
return of(data$);
}
}
public clear(): void {
this.store.dispatch(this.actions.clearCache());
}
private isCached(key: string): boolean {
return this.cacheStorage[key] !== undefined;
}
private addToCache<T>(key: string, value: T): void {
this.store.dispatch(this.actions.cache(key, value));
}
private getFromCache<T>(key: string): T {
return <T>this.cacheStorage[key];
}
private get cacheStorage(): { [key: string]: any } {
return this.store.getState().global.cache;
}
}
和使用示例:
// call without cache:
this.service.loadPeriods(param1, param2)
.pipe(...)
.subscribe(...)
// call with cache ("periods" is a cache key):
this.cache.get("periods", this.service, this.service.loadPeriods, param1, param2)
.pipe(...)
.subscribe(...);
答案 3 :(得分:1)
您可以创建内部键/值对存储解决方案来缓存请求。 在这里,我为此使用 Map()。
import { Injectable } from '@angular/core';
import { HttpEvent, HttpRequest, HttpHandler, HttpInterceptor, HttpResponse } from '@angular/common/http';
import { Observable, of } from 'rxjs';
import { tap, shareReplay } from 'rxjs/operators';
@Injectable()
export class CacheInterceptor implements HttpInterceptor {
private cache = new Map<string, any>();
intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
if (request.method !== 'GET') {
return next.handle(request);
}
const cachedResponse = this.cache.get(request.url);
if (cachedResponse) {
return of(cachedResponse);
}
return next.handle(request).pipe(
tap(event => {
if (event instanceof HttpResponse) {
this.cache.set(request.url, event);
}
})
);
}
}
现在,您需要照顾缓存失效。每当数据更改时,您都需要使它们无效。