angular - 将缓存的 HttpResponse 转换为 HttpClient 中的 Observable

标签 angular http caching

作为 Angular 4.3 HttpClient 功能的一部分,我正在使用拦截器来缓存和返回缓存数据。 下面是从拦截器调用的实用程序服务,用于存储和返回 HTTP 响应。

@Injectable()
export class LocalStorageCacheService implements HttpCache {
    get(req: HttpRequest<any>): HttpResponse<any> {
        return <HttpResponse<any>>JSON.parse(localStorage.getItem(btoa(req.url)))
    };
    put(req: HttpRequest<any>, resp: HttpResponse<any>): void {
        localStorage.setItem(btoa(req.url), JSON.stringify(resp));
    }
}

下面是我的拦截器,它检查缓存条目并在可用时返回。

@Injectable()
export class CacheInterceptorService implements HttpInterceptor {
    constructor(private localStorageCacheService: LocalStorageCacheService) {
    }
    intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
      if (req.method !== 'GET') {
          return next.handle(req);
        }
        const cachedResponse = this.localStorageCacheService.get(req);
        if (cachedResponse) {
         **return Observable.of(cachedResponse);**
        }
        return next.handle(req).do(event => {
          if (event instanceof HttpResponse) {
            this.localStorageCacheService.put(req, event);
          }
        });
      }
}

我遇到的问题是,http 调用没有命中调用组件的订阅部分。即声明 return Observable.of(cachedResponse); 似乎没有正确返回。

有什么想法吗?

更新 #1

我发现了问题,它显然是从 object 转换为 HttpResponse 类型由于某种原因没有发生,所以为了证明这一点,当我手动构建对象时使用普通对象,它开始工作。但显然,手动转换是一件肮脏的事情,需要弄清楚为什么转换不起作用。

if (cachedResponse) {

  let httpResponse = new HttpResponse({
    status : cachedResponse.status,
    body : cachedResponse.body,
    headers : cachedResponse.headers,
    statusText : cachedResponse.statusText,
    url : cachedResponse.url
  });

  return Observable.of(httpResponse)
};

最佳答案

像这样尝试:

intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    return <HttpRequest<any>>req.catch((error) => {
        return <HttpHandler>next.catch((err) => {
            if (req.method !== 'GET') {
                return next.handle(req);
            }
            const cachedResponse = this.localStorageCacheService.get(req);
            if (cachedResponse) {
                return Observable.throw(cachedResponse);
            }
            return next.handle(req).do(event => {
                if (event instanceof HttpResponse) {
                    this.localStorageCacheService.put(req, event);
                }
            });
        })
    })
}

关于angular - 将缓存的 HttpResponse 转换为 HttpClient 中的 Observable,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46842368/

相关文章:

angular - 在 sidenav 中编辑表单后重新获取/重新加载组件中的数据

angular - 堆栈 Blitz : How to import Bootstrap CSS framework

java - 在 Java 中将远程文件通过 HTTP 转换为输入流

javascript - 为什么这个 d3.text 请求失败了?

sql-server - 使用Redis实现的Sql Server内存表

javascript - Angular 2,如何将值存储在 ngOnInit() 的变量中?

Angular 2 : *ngFor does not update when array is updated

javascript - AJAX 从 HTTP 到 HTTPS

c# - .Net 缓存过期

java添加dns缓存记录