UNPKG

@kovalenko/http-request-cache

Version:

TS decorator for caching logic of API calls.

1 lines 8.41 kB
{"version":3,"file":"kovalenko-http-request-cache.mjs","sources":["../../../projects/http-request-cache/src/lib/default-storage.ts","../../../projects/http-request-cache/src/lib/request-times.ts","../../../projects/http-request-cache/src/lib/http-request-cache.decorator.ts","../../../projects/http-request-cache/src/public-api.ts","../../../projects/http-request-cache/src/kovalenko-http-request-cache.ts"],"sourcesContent":["import {HttpCacheStorage} from './http-cache-storage';\nimport {Observable} from 'rxjs';\n\nexport class DefaultStorage implements HttpCacheStorage {\n private storage = new Map<string, Observable<any>>();\n\n getItem(key: string): Observable<any> | undefined {\n return this.storage.get(key);\n }\n\n setItem(key: string, item: Observable<any>): void {\n this.storage.set(key, item);\n }\n\n deleteItem(key: string): void {\n this.storage.delete(key);\n }\n}\n","import {HttpCacheStorage} from './http-cache-storage';\nimport {Observable} from 'rxjs';\n\nexport class RequestTimes implements HttpCacheStorage {\n private storage = new Map<string, Observable<any>>();\n\n getItem(key: string): Observable<any> | undefined {\n return this.storage.get(key);\n }\n\n setItem(key: string, item: Observable<any>): void {\n this.storage.set(key, item);\n }\n\n deleteItem(key: string): void {\n this.storage.delete(key);\n }\n}\n","import {HttpCacheOptions} from './http-cache-options';\nimport {filter, finalize, merge, NEVER, Observable, Subject, tap, shareReplay, startWith, switchMap} from 'rxjs';\nimport {DefaultStorage} from './default-storage';\nimport {RequestTimes} from './request-times';\n\ntype HttpRequestCacheMethod = (...args: any[]) => Observable<any>;\n\nexport const HttpRequestCache = <T extends Record<string, any>>(optionsHandler?: (obj: T, ...args: any[]) => HttpCacheOptions) => {\n return (target: T, methodName: string, descriptor: TypedPropertyDescriptor<HttpRequestCacheMethod>): TypedPropertyDescriptor<HttpRequestCacheMethod> => {\n if (!(descriptor?.value instanceof Function)) {\n throw Error(`'@HttpRequestCache' can be applied only to the class method which returns an Observable`);\n }\n\n const cacheKeyPrefix = `${target.constructor.name}_${methodName}`;\n const originalMethod = descriptor.value;\n const working: Record<string, boolean> = {};\n let subscribers = 0;\n\n descriptor.value = function(...args: any[]): Observable<any> {\n const options = optionsHandler?.call(this as T, this as T, ...args);\n\n if (!options?.storage && !(target as any)._____storage_____) {\n (target as any)._____storage_____ = new DefaultStorage();\n }\n\n if (options?.ttl && !(target as any)._____ttl_storage_____) {\n (target as any)._____ttl_storage_____ = new RequestTimes();\n }\n\n const storage = options?.storage ?? (target as any)._____storage_____;\n\n const key = `${cacheKeyPrefix}_${JSON.stringify(args)}`;\n\n let ttl: {requestTime: number, subject: Subject<void>} = undefined as any;\n\n if (options?.ttl) {\n ttl = (target as any)._____ttl_storage_____.getItem(key);\n\n if (!ttl) {\n ttl = {\n requestTime: Date.now(),\n subject: new Subject(),\n };\n } else if (ttl.requestTime + options.ttl <= Date.now()) {\n working[key] = true;\n ttl.requestTime = Date.now();\n ttl.subject.next();\n }\n\n (target as any)._____ttl_storage_____.setItem(key, ttl);\n }\n\n const refreshOn = merge(\n options?.refreshOn ?? NEVER as Observable<unknown>,\n ttl?.subject ?? NEVER as Observable<unknown>,\n );\n\n let observable = storage.getItem(key);\n\n if (!observable) {\n observable = refreshOn.pipe(\n startWith(true),\n switchMap(() => originalMethod.apply(this, [...args])),\n tap(() => {\n delete working[key];\n }),\n shareReplay({\n bufferSize: 1,\n refCount: options?.refCount ?? false,\n windowTime: options?.windowTime ?? Infinity,\n }),\n filter(() => {\n return !working[key];\n }),\n finalize(() => {\n subscribers--;\n if (subscribers === 0 && options?.refCount) {\n storage.deleteItem(key);\n (target as any)._____ttl_storage_____?.deleteItem(key);\n }\n })\n );\n storage.setItem(key, observable);\n }\n\n subscribers++;\n\n return observable;\n };\n\n return descriptor;\n }\n}\n\n","/*\n * Public API Surface of http-request-cache\n */\n\nexport * from './lib/http-request-cache.decorator';\nexport * from './lib/http-cache-storage';\nexport * from './lib/http-cache-options';\nexport * from './lib/default-storage';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}