角度服务可实时将可观察对象/对象从缓存阵列返回到组件的多个实例 [英] Angular service that returns observables/subjects from a cache array to multiple instances of a component in realtime

查看:87
本文介绍了角度服务可实时将可观察对象/对象从缓存阵列返回到组件的多个实例的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

使用案例

我有一个内容页面,其中包含UserActionsComponent的多个实例.我还有一个全局DataService,它充当具有(想要)高级缓存的数据提供程序.

I have a content page that has multiple instances of UserActionsComponent. I also have a global DataService that acts as a data provider with (wannabe) advanced caching.

数据获取层次结构:

内存缓存>>浏览器存储(异步)>> HTTP请求

UserActionsComponent

请求dataService.getData(URL,params,method)

PS:params具有类似blogId的详细信息,这使哈希签名变得唯一

PS: params has details like blogId which makes the hash signature unique

DataService(.getData())

1)使用诸如genUniqueHash(URL + stringify(params)+ method)之类的东西制作唯一的哈希键

1) Makes a unique hash KEY using something like genUniqueHash(URL+stringify(params)+method)

2)检查内存缓存中是否存在值(数组[KEY])-如果是,则返回ob $

2) Checks if value is present in an in-memory cache (array[KEY]) - If yes, return ob$

3)检查浏览器的存储中是否存在值(异步;使用离子存储)-如果是,则返回ob $ else-保存到内存中的缓存中,然后返回ob $(array [KEY])

3) Check if value is present in browser's storage (async; uses Ionic storage) - If yes, return ob$ else - save to in-memory cache, then return ob$(array[KEY])

4)从HTTP调用获取值,保存到存储,保存到内存中的缓存并返回ob $(array [KEY])

4) Get the value from HTTP Call, save to Storage, save to in-memory cache and return ob$(array[KEY])

这个概念不起作用,因为我无法弄清如何从一组缓存值中返回一个共享的可观察对象(我猜这应该是一个BehaviourSubject?).请带我去正确的轨道.

This concept is not working as I am not able to figure out how to return a shared observable (I'm guessing this should be a BehaviourSubject?) from an array of cache values. Please bring me on the right track.

注释

  • 如果用户对某个组件投了赞成票,则它必须反映视图中的所有其他实例(所有特定Blog条目的UserActionsComponent都应更新)
  • 在同一页面上的一个视图中可以有许多UserActionsComponent(例如,对于BlogEntry#1和BlogEntry#25)!
  • 随着用户访问新的Blog帖子,内存中的高速缓存不断增长(这很好,因为它是一个有限的集合)

我是RxJS的菜鸟.我尝试过运气:

I'm a noob to RxJS. I tried my luck with:

  • pipe(share())[由于是一项服务,因此该管道已与所有URL共享]
  • 返回(cache [key])[不能工作,因为最后获取的BlogEntry的用户操作会反映所有订阅]
  • 返回整个缓存,然后在UserActionsComponent端过滤出所需的数据(使用array [KEY])(这是当前的实现)

当前的实现可行,但是对于这种用例来说,这似乎并不是最好的方法.原因是:一个视图可能具有多达20个UAC [UAC-A(1),UAC-B(1),UAC(200)...]. UAC发出两次next(). UAC的onInit以及用户在UAC中上投票或下票的时间.现在,由于更改,我们发出缓存数据,此页面视图的大小为20的数组发出2 * 20次.

The current implementation works, but it doesn't seem the best way to do it for this use case. Reason being: One view might have up-to 20 UACs [UAC-A(1), UAC-B(1), UAC(200) ...]. UAC emits next() twice. onInit of UAC and when user up-votes or down-votes in a UAC. Now since on change, we emit the cache data, an array of size 20 is emitted 2*20 times for this page view.

使用RxJS实现此目标的最优化方法是什么?

What would be the most optimized way to implement this using RxJS?

推荐答案

当前实现:

写下来,因为这对将来的人会有所帮助. 我设法通过可观察的模式对它进行了优化:

Writing it down as it would be helpful for someone in the future. I managed to optimize it using observable pattern this way:

  • UAC onInit()调用dataService.getData(url,params,method,guid)
  • UAC传递的guid是服务的缓存键
  • UAC有两个来自dataService的订阅.其中一个是dataService.getData方法,该方法返回一个可观察的对象-主要用作设置guid的初始化程序-在使用.pipe(first())获取其第一个值后便取消订阅.第二个订阅是一个名为dataChanged的BehaviourSubject.只要dataService缓存上的数据发生更改,它就会发出dataChanged.next(newDataDelta).该订阅将一直持续到组件的onDestroy.
  • dataService按cache[guid] > storage[guid] > http[url]进行分层检查,相应地设置数据,最后调用dataChangedSubj.next(cache[guid]) 仅会发出更改的增量
  • 所有UAC均接收新的缓存数据集(即cache [guid];仅包含已更改的内容),并检查receivedData[guid]以查看发出的数据是否与UAC相关.如果是,它将消耗它.
  • 如果用户在UAC上投票/否决,则UAC会进行必要的API调用,并在成功后执行dataService.updateData(guid,data),这反过来会使用dataChanged.next(newDataDelta)向所有UAC发出更改并且属于同一博客文章的UAC会更新其数据(因为它们的GUID相同)
  • UAC onInit() calls dataService.getData(url,params,method,guid)
  • The guid passed by the UAC is the cache key for the service
  • UAC has two subscriptions from dataService. One is dataService.getData method that returns an observable - mainly used as an initializer to set guid - it unsubscribes after getting its first value using .pipe(first()). Second subscription is to a BehaviourSubject called dataChanged. Whenever data is changed on dataService cache, it emits dataChanged.next(newDataDelta). This subscription persists till the component's onDestroy.
  • dataService checks hierarchically as cache[guid] > storage[guid] > http[url], sets data accordingly, and finally calls dataChangedSubj.next(cache[guid]) Only the changed delta would be emitted
  • All UACs receive the new cached DataSet (which is cache[guid]; contains only what was changed) and checks for receivedData[guid] to see if the emitted data is relevant to the UAC. If yes, it consumes it.
  • If user up-votes/down-votes on a UAC, UAC does necessary API calls, and on success, does dataService.updateData(guid,data), which in-turn emits the change using dataChanged.next(newDataDelta) to all UACs and the UACs that belong to the same blog post would update its data (as they would have the same guid)

仍然开放使用RxJS来实现此用例的最佳方法.

Still open for the best way to implement this use case using RxJS.

这篇关于角度服务可实时将可观察对象/对象从缓存阵列返回到组件的多个实例的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆