import { hash } from '@compiled/utils' ; import type { PluginOptions } from '../types' ; export interface CacheOptions extends PluginOptions { cache ? : boolean ; maxSize ? : number ; } const defaultOptions = { cache : true , maxSize : 500 , } ; export class Cache < T = any > { _options : CacheOptions & typeof defaultOptions = defaultOptions ; _cache : Map < string , T > ; constructor ( ) { this . _cache = new Map ( ) ; } param cacheKey param namespace static getUniqueKey ( cacheKey , namespace ? ) { return hash ( namespace ? `${ namespace }----${ cacheKey }` : cacheKey ) ; } param uniqueKey param value _saveToCache < TValue extends T > ( uniqueKey , value ) { const lazyValue = value ( ) ; this . _cache . set ( uniqueKey , lazyValue ) ; return lazyValue ; } /**
     * Deletes least recently used value (first in queue) from cache if cache size
     * reaches its max size.
     */ _tryDeletingLRUCachedValue ( ) { if ( this . _cache . size >= this . _options . maxSize ) { const key = this . _cache . keys ( ) . next ( ) . value ; this . _cache . delete ( key ) ; } } param uniqueKey param cacheValue _moveLastInQueue ( uniqueKey , cacheValue ) { this . _cache . delete ( uniqueKey ) ; this . _cache . set ( uniqueKey , cacheValue ) ; } param uniqueKey _loadFromCache < TValue extends T > ( uniqueKey ) { const cacheValue = this . _cache . get ( uniqueKey ) as TValue ; this . _moveLastInQueue ( uniqueKey , cacheValue ) ; return cacheValue ; } param options initialize ( options ) { this . _options = { ... defaultOptions , ... options } ; } param cacheKey param namespace param value load < TValue extends T > ( { cacheKey , namespace , value , } ) { if ( ! this . _options . cache ) { return value ( ) ; } const uniqueKey = Cache . getUniqueKey ( cacheKey , namespace ) ; if ( this . _cache . has ( uniqueKey ) ) { return this . _loadFromCache ( uniqueKey ) ; } this . _tryDeletingLRUCachedValue ( ) ; return this . _saveToCache ( uniqueKey , value ) ; } /**
     * Returns cache size
     */ getSize ( ) { return this . _cache . size ; } /**
     * Returns cache keys
     */ getKeys ( ) { return this . _cache . keys ( ) ; } /**
     * Returns cache values
     */ getValues ( ) { return this . _cache . values ( ) ; } }