{"version":3,"file":"index.cjs","sources":["../core/src//main/index.ts","../core/src//constants.ts"],"sourcesContent":["import { instance } from '@cachemap/controller';\nimport { MapStore } from '@cachemap/map';\nimport { type DehydratedMetadata, type Metadata, type Store, type Tag } from '@cachemap/types';\nimport {\n  ArgsError,\n  GroupedError,\n  PositionError,\n  ValueFormat,\n  constants,\n  dehydrateMetadata,\n  isJsonValue,\n  prepareGetEntry,\n  prepareSetEntry,\n  rehydrateMetadata,\n  sizeOf,\n} from '@cachemap/utils';\nimport { Cacheability } from 'cacheability';\nimport { EventEmitter } from 'eventemitter3';\nimport { castArray, get, isArray, isFunction, isNumber, isPlainObject, isString, isUndefined } from 'lodash-es';\nimport { Md5 } from 'ts-md5';\nimport { type JsonValue } from 'type-fest';\nimport { DEFAULT_BACKUP_INTERVAL, DEFAULT_MAX_HEAP_SIZE } from '../constants.ts';\nimport {\n  type ConstructorOptions,\n  type ControllerEvent,\n  type ExportOptions,\n  type ExportResult,\n  type ImportOptions,\n  type MethodName,\n  type Reaper,\n  type ReaperInit,\n  type RequestQueue,\n  type SetOptions,\n} from '../types.ts';\n\nexport class Core {\n  public events = {\n    ENTRY_DELETED: 'ENTRY_DELETED',\n  };\n\n  private static _sortComparator = (a: Metadata, b: Metadata): number => {\n    let index;\n\n    if (a.accessedCount > b.accessedCount) {\n      index = -1;\n    } else if (a.accessedCount < b.accessedCount) {\n      index = 1;\n    } else if (a.lastAccessed > b.lastAccessed) {\n      index = -1;\n    } else if (a.lastAccessed < b.lastAccessed) {\n      index = 1;\n    } else if (a.lastUpdated > b.lastUpdated) {\n      index = -1;\n    } else if (a.lastUpdated < b.lastUpdated) {\n      index = 1;\n    } else if (a.added > b.added) {\n      index = -1;\n    } else if (a.added < b.added) {\n      index = 1;\n    } else if (a.size < b.size) {\n      index = -1;\n    } else if (a.size > b.size) {\n      index = 1;\n    } else {\n      index = 0;\n    }\n\n    return index;\n  };\n\n  private _handleClearEvent = ({ name, type }: ControllerEvent): void => {\n    if ((isString(name) && name === this._name) || (isString(type) && type === this._type)) {\n      void this._clear();\n    }\n  };\n\n  private _handleStartReaperEvent = ({ name, type }: ControllerEvent): void => {\n    if ((isString(name) && name === this._name) || (isString(type) && type === this._type)) {\n      this._reaper?.start();\n    }\n  };\n\n  private _handleStopReaperEvent = ({ name, type }: ControllerEvent): void => {\n    if ((isString(name) && name === this._name) || (isString(type) && type === this._type)) {\n      this._reaper?.stop();\n    }\n  };\n\n  private _handleStartBackupEvent = ({ name, type }: ControllerEvent): void => {\n    if ((isString(name) && name === this._name) || (isString(type) && type === this._type)) {\n      this._startBackup();\n    }\n  };\n\n  private _handleStopBackupEvent = ({ name, type }: ControllerEvent): void => {\n    if ((isString(name) && name === this._name) || (isString(type) && type === this._type)) {\n      this._stopBackup();\n    }\n  };\n\n  private _backupInterval: number = DEFAULT_BACKUP_INTERVAL;\n  private _backupIntervalID?: NodeJS.Timeout;\n  private _backupStore?: Store;\n  private readonly _disableCacheInvalidation: boolean;\n  private _emitter: EventEmitter = new EventEmitter();\n  private readonly _encryptionSecret: string | undefined;\n  private _maxHeapSize: number = DEFAULT_MAX_HEAP_SIZE;\n  private _metadata: Metadata[] = [];\n  private readonly _name: string;\n  private _persistedStore = true;\n  private _processing: string[] = [];\n  private _ready = false;\n  private readonly _reaper?: Reaper;\n  private _requestQueue: RequestQueue = [];\n  private readonly _sharedCache: boolean;\n  private _store?: Store;\n  private readonly _type: string;\n  private _usedHeapSize = 0;\n  private readonly _valueFormatting: ValueFormat = ValueFormat.String;\n\n  constructor(options: ConstructorOptions) {\n    const errors: ArgsError[] = [];\n\n    if (!isPlainObject(options)) {\n      errors.push(new ArgsError('@cachemap/core expected options to be a plain object.'));\n    }\n\n    if (!isString(options.name)) {\n      errors.push(new ArgsError('@cachemap/core expected options.name to be a string.'));\n    }\n\n    if (!isFunction(options.store)) {\n      errors.push(new ArgsError('@cachemap/core expected options.store to be a function.'));\n    }\n\n    if (!isString(options.type)) {\n      errors.push(new ArgsError('@cachemap/core expected options.type to be a string.'));\n    }\n\n    if (options.valueFormatting === ValueFormat.Ecrypt && !options.encryptionSecret) {\n      errors.push(\n        new ArgsError('@cachemap/core expected encryptionSecret to be set when valueFormatting is \"encrypt\"'),\n      );\n    }\n\n    if (errors.length > 0) {\n      throw new GroupedError('@cachemap/core constructor argument validation errors.', errors);\n    }\n\n    const {\n      backupInterval,\n      backupStore,\n      disableCacheInvalidation = false,\n      encryptionSecret,\n      name,\n      reaper,\n      sharedCache = false,\n      sortComparator,\n      startBackup,\n      store: storeInit,\n      type,\n      valueFormatting,\n    } = options;\n\n    this._disableCacheInvalidation = disableCacheInvalidation;\n\n    if (valueFormatting) {\n      this._valueFormatting = valueFormatting;\n    }\n\n    if (isString(encryptionSecret)) {\n      this._encryptionSecret = encryptionSecret;\n    }\n\n    this._name = name;\n\n    if (isFunction(reaper)) {\n      this._reaper = this._initializeReaper(reaper);\n    }\n\n    this._sharedCache = sharedCache;\n\n    if (isFunction(sortComparator)) {\n      Core._sortComparator = sortComparator;\n    }\n\n    this._type = type;\n    this._addControllerEventListeners();\n\n    void Promise.resolve(storeInit({ name })).then(async store => {\n      this._maxHeapSize = store.maxHeapSize;\n\n      if (backupStore) {\n        if (store.type === 'map') {\n          throw new ArgsError(\"@cachemap/core expected store.type not to be 'map' when backupStore is true.\");\n        }\n\n        if (isNumber(backupInterval)) {\n          this._backupInterval = backupInterval;\n        }\n\n        this._backupStore = store;\n        this._persistedStore = true;\n        this._store = new MapStore({ maxHeapSize: store.maxHeapSize, name });\n        await this._backupStoreEntriesToStore();\n        this._ready = true;\n        void this._releaseQueuedRequests();\n\n        if (startBackup) {\n          this._startBackup();\n        }\n      } else {\n        this._persistedStore = store.type !== 'map';\n        this._store = store;\n        await this._retreiveMetadataFromStore();\n        this._ready = true;\n        void this._releaseQueuedRequests();\n      }\n    });\n  }\n\n  public async clear(): Promise<void> {\n    return this._clear();\n  }\n\n  public async delete(key: string, options: { hashKey?: boolean } = {}): Promise<boolean> {\n    const errors: ArgsError[] = [];\n\n    if (!isString(key)) {\n      errors.push(new ArgsError('@cachemap/core expected key to be a string.'));\n    }\n\n    if (!isPlainObject(options)) {\n      errors.push(new ArgsError('@cachemap/core expected options to be a plain object.'));\n    }\n\n    if (errors.length > 0) {\n      throw new GroupedError('@cachemap/core delete argument validation errors.', errors);\n    }\n\n    return this._delete(key, options);\n  }\n\n  get emitter(): EventEmitter {\n    return this._emitter;\n  }\n\n  public async entries<T>(keys?: string[]): Promise<[string, T][]> {\n    if (keys && !isArray(keys)) {\n      throw new ArgsError('@cachemap/core expected keys to be an array.');\n    }\n\n    const entries = await this._entries<T>(keys);\n\n    return entries.sort(([a], [b]) => {\n      if (a < b) {\n        return -1;\n      }\n\n      if (a > b) {\n        return 1;\n      }\n\n      return 0;\n    });\n  }\n\n  public async export<T>(options: ExportOptions = {}): Promise<ExportResult<T>> {\n    const errors: ArgsError[] = [];\n\n    if (!isPlainObject(options)) {\n      errors.push(new ArgsError('@cachemap/core expected options to be an plain object.'));\n    }\n\n    if (options.keys && !isArray(options.keys)) {\n      errors.push(new ArgsError('@cachemap/core expected options.keys to be an array.'));\n    }\n\n    if (errors.length > 0) {\n      throw new GroupedError('@cachemap/core export argument validation errors.', errors);\n    }\n\n    const { entries, metadata } = await this._export<T>(options);\n\n    return {\n      entries: entries.sort(([a], [b]) => {\n        if (a < b) {\n          return -1;\n        }\n\n        if (a > b) {\n          return 1;\n        }\n\n        return 0;\n      }),\n      metadata: metadata.sort((a, b) => {\n        if (a.key < b.key) {\n          return -1;\n        }\n\n        if (a.key > b.key) {\n          return 1;\n        }\n\n        return 0;\n      }),\n    };\n  }\n\n  public async get<T>(key: string, options: { hashKey?: boolean } = {}): Promise<T | undefined> {\n    const errors: ArgsError[] = [];\n\n    if (!isString(key)) {\n      errors.push(new ArgsError('@cachemap/core expected key to be a string.'));\n    }\n\n    if (!isPlainObject(options)) {\n      errors.push(new ArgsError('@cachemap/core expected options to be a plain object.'));\n    }\n\n    if (errors.length > 0) {\n      throw new GroupedError('@cachemap/core get argument validation errors.', errors);\n    }\n\n    return this._get<T>(key, options);\n  }\n\n  public getMetadataEntry(rawkey: string, options: { hashKey?: boolean } = {}): Metadata | undefined {\n    const key = options.hashKey ? Md5.hashStr(rawkey) : rawkey;\n    return this._getMetadataEntry(key);\n  }\n\n  public async has(\n    key: string,\n    options: { deleteExpired?: boolean; hashKey?: boolean } = {},\n  ): Promise<false | Cacheability> {\n    const errors: ArgsError[] = [];\n\n    if (!isString(key)) {\n      errors.push(new ArgsError('@cachemap/core expected key to be a string.'));\n    }\n\n    if (!isPlainObject(options)) {\n      errors.push(new ArgsError('@cachemap/core expected opts to be a plain object.'));\n    }\n\n    if (errors.length > 0) {\n      throw new GroupedError('@cachemap/core has argument validation errors.', errors);\n    }\n\n    return this._has(key, options);\n  }\n\n  public async import(options: ImportOptions): Promise<void> {\n    if (!isPlainObject(options)) {\n      throw new ArgsError('@cachemap/core expected options to be a plain object.');\n    }\n\n    const { entries, metadata } = options;\n    const errors: ArgsError[] = [];\n\n    if (!isArray(entries)) {\n      errors.push(new ArgsError('@cachemap/core expected entries to be an array.'));\n    }\n\n    if (!isArray(metadata)) {\n      errors.push(new ArgsError('@cachemap/core expected metadata to be an array.'));\n    }\n\n    if (errors.length > 0) {\n      throw new GroupedError('@cachemap/core has argument validation errors.', errors);\n    }\n\n    return this._import(options);\n  }\n\n  get metadata(): Metadata[] {\n    return this._metadata;\n  }\n\n  get name(): string {\n    return this._name;\n  }\n\n  get reaper(): Reaper | undefined {\n    return this._reaper;\n  }\n\n  public async set(key: string, value: unknown, options: SetOptions = {}): Promise<void> {\n    const errors: ArgsError[] = [];\n\n    if (!isString(key)) {\n      errors.push(new ArgsError('@cachemap/core expected key to be a string.'));\n    }\n\n    if (!isPlainObject(options)) {\n      errors.push(new ArgsError('@cachemap/core expected options to be a plain object.'));\n    }\n\n    if (!isJsonValue(value)) {\n      errors.push(new ArgsError('@cachemap/core expected value to be JSON serializable.'));\n    }\n\n    if (errors.length > 0) {\n      throw new GroupedError('@cachemap/core set argument validation errors.', errors);\n    }\n\n    // typescript not deriving value is JsonValue from above type guard.\n    // eslint-disable-next-line @typescript-eslint/consistent-type-assertions\n    return this._set(key, value as JsonValue, options);\n  }\n\n  public async size(): Promise<number> {\n    return this._size();\n  }\n\n  public startBackup(): void {\n    this._startBackup();\n  }\n\n  public stopBackup(): void {\n    this._stopBackup();\n  }\n\n  get storeType(): string {\n    return this._store?.type ?? 'none';\n  }\n\n  get type(): string {\n    return this._type;\n  }\n\n  get usedHeapSize(): number {\n    return this._usedHeapSize;\n  }\n\n  private _addControllerEventListeners(): void {\n    instance.on(constants.CLEAR, this._handleClearEvent);\n    instance.on(constants.START_REAPER, this._handleStartReaperEvent);\n    instance.on(constants.STOP_REAPER, this._handleStopReaperEvent);\n    instance.on(constants.START_BACKUP, this._handleStartBackupEvent);\n    instance.on(constants.STOP_BACKUP, this._handleStopBackupEvent);\n  }\n\n  private async _addMetadata(\n    key: string,\n    size: number,\n    cacheability: Cacheability,\n    tag?: Tag,\n    extensions?: Record<string, unknown>,\n  ): Promise<void> {\n    this._metadata.push({\n      accessedCount: 0,\n      added: Date.now(),\n      cacheability,\n      extensions,\n      key,\n      lastAccessed: Date.now(),\n      lastUpdated: Date.now(),\n      size,\n      tags: tag ? [tag] : [],\n      updatedCount: 0,\n    });\n\n    this._sortMetadata();\n    this._updateHeapSize();\n    return this._backupMetadata();\n  }\n\n  private _addRequestToQueue<T>(methodName: MethodName, ...payload: unknown[]): Promise<T> {\n    return new Promise((resolve: (value: T) => void) => {\n      this._requestQueue.push([resolve, methodName, payload]);\n    });\n  }\n\n  private async _backupMetadata(): Promise<void> {\n    if (!this._store || !this._persistedStore) {\n      return;\n    }\n\n    const store = this._backupStore ?? this._store;\n\n    return store.set(\n      constants.METADATA,\n      // metadata is serializable as JSON.\n      // eslint-disable-next-line @typescript-eslint/consistent-type-assertions\n      prepareSetEntry(dehydrateMetadata(this._metadata) as JsonValue, this._valueFormatting, this._encryptionSecret),\n    );\n  }\n\n  private async _backupStoreEntriesToStore(): Promise<void> {\n    if (!(this._backupStore && this._store)) {\n      throw new PositionError(\n        '@cachemap/core expected backupStoreEntriesToStore to be called after setting the backupStore and store.',\n      );\n    }\n\n    this._metadata = [];\n    const backupMetadata = await this._backupStore.get(constants.METADATA);\n\n    if (backupMetadata) {\n      const metadata = prepareGetEntry<DehydratedMetadata[]>(\n        backupMetadata,\n        this._valueFormatting,\n        this._encryptionSecret,\n      );\n\n      if (metadata.length > 0) {\n        const keys = metadata.map(entry => entry.key);\n        await this._store.import(await this._backupStore.entries(keys));\n        this._metadata = rehydrateMetadata(metadata);\n      }\n    }\n  }\n\n  private _calcReductionChunk(): number | undefined {\n    const reductionSize = Math.round(this._maxHeapSize * 0.2);\n    let chunkSize = 0;\n    let chunk: number | undefined;\n\n    for (let index = this._metadata.length - 1; index >= 0; index -= 1) {\n      // Based on surrounding code context, this cannot be undefined.\n      // eslint-disable-next-line @typescript-eslint/no-non-null-assertion\n      chunkSize += this._metadata[index]!.size;\n\n      if (chunkSize > reductionSize) {\n        chunk = index;\n        break;\n      }\n    }\n\n    return chunk;\n  }\n\n  private _cleanupTag(tag: string | number): void {\n    for (const entry of this._metadata) {\n      if (entry.tags.includes(tag)) {\n        entry.tags = entry.tags.filter(t => t !== tag);\n      }\n    }\n  }\n\n  private async _clear(): Promise<void> {\n    if (!this._ready || !this._store) {\n      return this._addRequestToQueue(constants.CLEAR);\n    }\n\n    await this._store.clear();\n    this._metadata = [];\n    this._processing = [];\n    this._updateHeapSize();\n    return this._backupMetadata();\n  }\n\n  private async _delete(key: string, options: { hashKey?: boolean } = {}): Promise<boolean> {\n    if (!this._ready || !this._store) {\n      return this._addRequestToQueue(constants.DELETE, key, options);\n    }\n\n    const deleteKey = options.hashKey ? Md5.hashStr(key) : key;\n    const deleted = await this._store.delete(deleteKey);\n\n    if (!deleted) {\n      return false;\n    }\n\n    await this._deleteMetadata(deleteKey);\n    return true;\n  }\n\n  private async _deleteMetadata(key: string): Promise<void> {\n    const index = this._metadata.findIndex(metadata => metadata.key === key);\n\n    if (index === -1) {\n      return;\n    }\n\n    this._metadata.splice(index, 1);\n    this._sortMetadata();\n    this._updateHeapSize();\n    return this._backupMetadata();\n  }\n\n  private async _entries<T>(keys?: string[]): Promise<[string, T][]> {\n    if (!this._ready || !this._store) {\n      return this._addRequestToQueue(constants.ENTRIES, keys);\n    }\n\n    const entryKeys = keys ?? this._metadata.map(metadata => metadata.key);\n    const entries = await this._store.entries(entryKeys);\n    return entries.map(([key, data]) => [key, prepareGetEntry(data, this._valueFormatting, this._encryptionSecret)]);\n  }\n\n  private async _export<T>({ cleanupTag, filterByValue, keys, tag }: ExportOptions): Promise<ExportResult<T>> {\n    let exportKeys: string[] | undefined;\n    let metadata = [...this._metadata];\n\n    if (tag) {\n      metadata = this._metadata.filter(meta => meta.tags.includes(tag));\n      exportKeys = metadata.map(meta => meta.key);\n\n      if (cleanupTag) {\n        this._cleanupTag(tag);\n      }\n    } else if (keys) {\n      metadata = this._metadata.filter(meta => keys.includes(meta.key));\n      exportKeys = keys;\n    }\n\n    let entries = await this._entries<T>(exportKeys);\n\n    if (filterByValue) {\n      const castFilterByValue = castArray(filterByValue);\n\n      entries = entries.filter(([, data]) =>\n        castFilterByValue.every(({ comparator, keyChain }) => get(data, keyChain) === comparator),\n      );\n\n      metadata = metadata.filter(meta => entries.some(([key]) => key === meta.key));\n    }\n\n    return { entries, metadata };\n  }\n\n  private async _get<T>(key: string, options: { deleteExpired?: boolean; hashKey?: boolean }): Promise<T | undefined> {\n    if (!this._ready || !this._store) {\n      return this._addRequestToQueue(constants.GET, key, options);\n    }\n\n    const getKey = options.hashKey ? Md5.hashStr(key) : key;\n    const hasExpired = this._hasCacheEntryExpired(getKey);\n\n    if (hasExpired) {\n      if (options.deleteExpired) {\n        await this._delete(getKey);\n      }\n\n      return;\n    }\n\n    const value = await this._store.get(getKey);\n\n    if (!value) {\n      return;\n    }\n\n    await this._updateMetadata(getKey);\n    return prepareGetEntry(value, this._valueFormatting, this._encryptionSecret);\n  }\n\n  private _getCacheability(key: string): Cacheability | undefined {\n    const metadata = this._getMetadataEntry(key);\n    return metadata ? metadata.cacheability : undefined;\n  }\n\n  private _getMetadataEntry(key: string): Metadata | undefined {\n    return this._metadata.find(metadata => metadata.key === key);\n  }\n\n  private async _has(\n    key: string,\n    options: { deleteExpired?: boolean; hashKey?: boolean },\n  ): Promise<false | Cacheability> {\n    if (!this._ready || !this._store) {\n      return this._addRequestToQueue(constants.HAS, key, options);\n    }\n\n    const hasKey = options.hashKey ? Md5.hashStr(key) : key;\n    const hasExpired = this._hasCacheEntryExpired(hasKey);\n\n    if (hasExpired) {\n      if (options.deleteExpired) {\n        await this._delete(hasKey);\n      }\n\n      return false;\n    }\n\n    const exists = await this._store.has(hasKey);\n\n    if (!exists) {\n      return false;\n    }\n\n    return this._getCacheability(hasKey) ?? false;\n  }\n\n  private _hasCacheEntryExpired(key: string): boolean {\n    if (this._disableCacheInvalidation) {\n      return false;\n    }\n\n    const cacheability = this._getCacheability(key);\n    return cacheability ? !cacheability.checkTTL() : false;\n  }\n\n  private async _import(options: ImportOptions): Promise<void> {\n    if (!this._ready || !this._store) {\n      return this._addRequestToQueue(constants.IMPORT, options);\n    }\n\n    let filtered: Metadata[] = [];\n\n    if (this._metadata.length > 0) {\n      filtered = this._metadata.filter(metadata => {\n        return !options.metadata.some(optionsMetadata => metadata.key === optionsMetadata.key);\n      });\n    }\n\n    const entries = options.entries.map(\n      // typescript is not seeing this as a string tuple.\n      // eslint-disable-next-line @typescript-eslint/consistent-type-assertions\n      ([key, data]) => [key, prepareSetEntry(data, this._valueFormatting, this._encryptionSecret)] as [string, string],\n    );\n\n    await this._store.import(entries);\n    this._metadata = rehydrateMetadata([...filtered, ...options.metadata]);\n    this._sortMetadata();\n    await this._backupMetadata();\n    this._updateHeapSize();\n  }\n\n  private _initializeReaper(reaperInit: ReaperInit): Reaper {\n    return reaperInit({\n      deleteCallback: async (key: string, tags?: Tag[]) => {\n        this.emitter.emit(this.events.ENTRY_DELETED, { deleted: await this._delete(key), key, tags });\n      },\n      metadataCallback: () => this._metadata,\n    });\n  }\n\n  private _processed(key: string): void {\n    this._processing = this._processing.filter(value => value !== key);\n  }\n\n  private _reduceHeapSize(): void {\n    const index = this._calcReductionChunk();\n\n    if (!index || !this._reaper) {\n      return;\n    }\n\n    void this._reaper.cull(this._metadata.slice(index));\n  }\n\n  private async _releaseQueuedRequests(): Promise<void> {\n    for (const [resolve, methodName, payload] of this._requestQueue) {\n      // @ts-expect-error complicated\n      resolve(await this[methodName](...payload));\n    }\n\n    this._requestQueue = [];\n  }\n\n  private async _retreiveMetadataFromStore(): Promise<void> {\n    if (!this._store || !this._persistedStore) {\n      return;\n    }\n\n    const metadata = await this._store.get(constants.METADATA);\n\n    if (metadata) {\n      this._metadata = rehydrateMetadata(prepareGetEntry(metadata, this._valueFormatting, this._encryptionSecret));\n    }\n  }\n\n  private async _set(key: string, value: JsonValue, options: SetOptions): Promise<void> {\n    if (!this._ready || !this._store) {\n      return this._addRequestToQueue(constants.SET, key, value, options);\n    }\n\n    const cacheability = new Cacheability(options.cacheOptions);\n    const { cacheControl } = cacheability.metadata;\n\n    if (cacheControl.noStore || (this._sharedCache && cacheControl.private)) {\n      return;\n    }\n\n    const setKey = options.hashKey ? Md5.hashStr(key) : key;\n    const processing = this._processing.includes(setKey);\n\n    if (!processing) {\n      this._processing.push(setKey);\n    }\n\n    try {\n      const exists = (await this._store.has(setKey)) || processing;\n      const preparedSetValue = prepareSetEntry(value, this._valueFormatting, this._encryptionSecret);\n      await this._store.set(setKey, preparedSetValue);\n\n      await (exists\n        ? this._updateMetadata(setKey, sizeOf(preparedSetValue), cacheability, options.tag, options.extensions)\n        : this._addMetadata(setKey, sizeOf(preparedSetValue), cacheability, options.tag, options.extensions));\n\n      this._processed(setKey);\n    } catch (error) {\n      this._processed(setKey);\n      throw error;\n    }\n  }\n\n  private async _size(): Promise<number> {\n    if (!this._ready || !this._store) {\n      return this._addRequestToQueue(constants.SIZE);\n    }\n\n    return this._store.size();\n  }\n\n  private _sortMetadata(): void {\n    this._metadata.sort(Core._sortComparator);\n  }\n\n  private _startBackup(): void {\n    this._backupIntervalID = setInterval(() => {\n      void this._storeEntriesToBackupStore();\n    }, this._backupInterval);\n  }\n\n  private _stopBackup(): void {\n    if (this._backupIntervalID) {\n      clearInterval(this._backupIntervalID);\n    }\n  }\n\n  private async _storeEntriesToBackupStore(): Promise<void> {\n    if (!(this._backupStore && this._store)) {\n      return;\n    }\n\n    const keys = this._metadata.map(entry => entry.key);\n    void this._backupStore.import(await this._store.entries(keys));\n  }\n\n  private _updateHeapSize(): void {\n    this._usedHeapSize = this._metadata.reduce((acc, value) => acc + value.size, 0);\n\n    if (!this._disableCacheInvalidation && this._usedHeapSize > this._maxHeapSize) {\n      this._reduceHeapSize();\n    }\n  }\n\n  private async _updateMetadata(\n    key: string,\n    size?: number,\n    cacheability?: Cacheability,\n    tag?: Tag,\n    extensions?: Record<string, unknown>,\n  ): Promise<void> {\n    const entry = this._getMetadataEntry(key);\n\n    if (!entry) {\n      return;\n    }\n\n    if (size) {\n      entry.size = size;\n      entry.lastUpdated = Date.now();\n      entry.updatedCount += 1;\n    } else {\n      entry.accessedCount += 1;\n      entry.lastAccessed = Date.now();\n    }\n\n    if (cacheability) {\n      entry.cacheability = cacheability;\n    }\n\n    if (!isUndefined(tag)) {\n      entry.tags.push(tag);\n    }\n\n    if (extensions) {\n      entry.extensions = Object.assign(entry.extensions ?? {}, extensions);\n    }\n\n    this._sortMetadata();\n    this._updateHeapSize();\n    return this._backupMetadata();\n  }\n}\n","export const DEFAULT_MAX_HEAP_SIZE = 4_194_304;\nexport const DEFAULT_BACKUP_INTERVAL = 10_000;\n"],"names":["Core","_sortComparator","a","b","index","accessedCount","lastAccessed","lastUpdated","added","size","constructor","options","events","ENTRY_DELETED","_handleClearEvent","name","type","isString","this","_name","_type","_clear","_handleStartReaperEvent","_reaper","start","_handleStopReaperEvent","stop","_handleStartBackupEvent","_startBackup","_handleStopBackupEvent","_stopBackup","_backupInterval","_emitter","EventEmitter","_maxHeapSize","_metadata","_persistedStore","_processing","_ready","_requestQueue","_usedHeapSize","_valueFormatting","ValueFormat","String","errors","isPlainObject","push","ArgsError","isFunction","store","valueFormatting","Ecrypt","encryptionSecret","length","GroupedError","backupInterval","backupStore","disableCacheInvalidation","reaper","sharedCache","sortComparator","startBackup","storeInit","_disableCacheInvalidation","_encryptionSecret","_initializeReaper","_sharedCache","_addControllerEventListeners","Promise","resolve","then","async","maxHeapSize","isNumber","_backupStore","_store","MapStore","_backupStoreEntriesToStore","_releaseQueuedRequests","_retreiveMetadataFromStore","clear","delete","key","_delete","emitter","entries","keys","isArray","_entries","sort","export","metadata","_export","get","_get","getMetadataEntry","rawkey","hashKey","Md5","hashStr","_getMetadataEntry","has","_has","import","_import","set","value","isJsonValue","_set","_size","stopBackup","storeType","usedHeapSize","instance","on","constants","CLEAR","START_REAPER","STOP_REAPER","START_BACKUP","STOP_BACKUP","_addMetadata","cacheability","tag","extensions","Date","now","tags","updatedCount","_sortMetadata","_updateHeapSize","_backupMetadata","_addRequestToQueue","methodName","payload","METADATA","prepareSetEntry","dehydrateMetadata","PositionError","backupMetadata","prepareGetEntry","map","entry","rehydrateMetadata","_calcReductionChunk","reductionSize","Math","round","chunk","chunkSize","_cleanupTag","includes","filter","t","DELETE","deleteKey","_deleteMetadata","findIndex","splice","ENTRIES","entryKeys","data","cleanupTag","filterByValue","exportKeys","meta","castFilterByValue","castArray","every","comparator","keyChain","some","GET","getKey","_hasCacheEntryExpired","deleteExpired","_updateMetadata","_getCacheability","undefined","find","HAS","hasKey","checkTTL","IMPORT","filtered","optionsMetadata","reaperInit","deleteCallback","emit","deleted","metadataCallback","_processed","_reduceHeapSize","cull","slice","SET","Cacheability","cacheOptions","cacheControl","noStore","private","setKey","processing","exists","preparedSetValue","sizeOf","error","SIZE","_backupIntervalID","setInterval","_storeEntriesToBackupStore","clearInterval","reduce","acc","isUndefined","Object","assign"],"mappings":"oRAmCO,MAAMA,SAKIC,KAAAA,gBAAkB,CAACC,EAAaC,KAC7C,IAAIC,EA0BJ,OAvBEA,EADEF,EAAEG,cAAgBF,EAAEE,eACd,EACCH,EAAEG,cAAgBF,EAAEE,cACrB,EACCH,EAAEI,aAAeH,EAAEG,cACpB,EACCJ,EAAEI,aAAeH,EAAEG,aACpB,EACCJ,EAAEK,YAAcJ,EAAEI,aACnB,EACCL,EAAEK,YAAcJ,EAAEI,YACnB,EACCL,EAAEM,MAAQL,EAAEK,OACb,EACCN,EAAEM,MAAQL,EAAEK,MACb,EACCN,EAAEO,KAAON,EAAEM,MACZ,EACCP,EAAEO,KAAON,EAAEM,KACZ,EAEA,EAGHL,CAAAA,EAqDT,WAAAM,CAAYC,QApFLC,OAAS,CACdC,cAAe,iBAiCTC,KAAAA,kBAAoB,EAAGC,OAAMC,YAC/BC,WAAUF,IAASA,IAASG,KAAKC,OAAWF,EAAAA,SAASD,IAASA,IAASE,KAAKE,QACzEF,KAAKG,QACZ,EAGMC,KAAAA,wBAA0B,EAAGP,OAAMC,YACrCC,WAAUF,IAASA,IAASG,KAAKC,OAAWF,EAAAA,SAASD,IAASA,IAASE,KAAKE,QAC9EF,KAAKK,SAASC,OAChB,EAGMC,KAAAA,uBAAyB,EAAGV,OAAMC,YACpCC,WAAUF,IAASA,IAASG,KAAKC,OAAWF,EAAAA,SAASD,IAASA,IAASE,KAAKE,QAC9EF,KAAKK,SAASG,MAChB,EAGMC,KAAAA,wBAA0B,EAAGZ,OAAMC,YACrCC,WAAUF,IAASA,IAASG,KAAKC,OAAWF,EAAAA,SAASD,IAASA,IAASE,KAAKE,QAC9EF,KAAKU,cACP,EAGMC,KAAAA,uBAAyB,EAAGd,OAAMC,YACpCC,WAAUF,IAASA,IAASG,KAAKC,OAAWF,EAAAA,SAASD,IAASA,IAASE,KAAKE,QAC9EF,KAAKY,aACP,OAGMC,gBCnG6B,IDuG7BC,KAAAA,SAAyB,IAAIC,oBAE7BC,aC1G2B,QD2G3BC,KAAAA,UAAwB,QAExBC,iBAAkB,EAClBC,KAAAA,YAAwB,QACxBC,QAAS,EAETC,KAAAA,cAA8B,QAI9BC,cAAgB,EACPC,KAAAA,iBAAgCC,EAAAA,YAAYC,OAG3D,MAAMC,EAAsB,GAwB5B,GAtBKC,EAAAA,cAAclC,IACjBiC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,0DAGvB9B,EAAAA,SAASN,EAAQI,OACpB6B,EAAOE,KAAK,IAAIC,EAAAA,UAAU,yDAGvBC,EAAAA,WAAWrC,EAAQsC,QACtBL,EAAOE,KAAK,IAAIC,EAAAA,UAAU,4DAGvB9B,EAAAA,SAASN,EAAQK,OACpB4B,EAAOE,KAAK,IAAIC,EAAAA,UAAU,yDAGxBpC,EAAQuC,kBAAoBR,EAAAA,YAAYS,QAAWxC,EAAQyC,kBAC7DR,EAAOE,KACL,IAAIC,EAAAA,UAAU,yFAIdH,EAAOS,OAAS,EAClB,MAAM,IAAIC,EAAAA,aAAa,yDAA0DV,GAGnF,MAAMW,eACJA,EAAcC,YACdA,EAAWC,yBACXA,GAA2B,EAAKL,iBAChCA,EAAgBrC,KAChBA,EAAI2C,OACJA,EAAMC,YACNA,GAAc,EAAKC,eACnBA,EAAcC,YACdA,EACAZ,MAAOa,EAAS9C,KAChBA,EAAIkC,gBACJA,GACEvC,EAEJO,KAAK6C,0BAA4BN,EAE7BP,IACFhC,KAAKuB,iBAAmBS,GAGtBjC,EAAAA,SAASmC,KACXlC,KAAK8C,kBAAoBZ,GAG3BlC,KAAKC,MAAQJ,EAETiC,EAAAA,WAAWU,KACbxC,KAAKK,QAAUL,KAAK+C,kBAAkBP,IAGxCxC,KAAKgD,aAAeP,EAEhBX,EAAAA,WAAWY,KACb5D,EAAKC,gBAAkB2D,GAGzB1C,KAAKE,MAAQJ,EACbE,KAAKiD,+BAEAC,QAAQC,QAAQP,EAAU,CAAE/C,UAASuD,MAAKC,MAAMtB,IAGnD,GAFA/B,KAAKgB,aAAee,EAAMuB,YAEtBhB,EAAa,CACf,GAAmB,QAAfP,EAAMjC,KACR,MAAM,IAAI+B,EAAAA,UAAU,gFAGlB0B,EAAAA,SAASlB,KACXrC,KAAKa,gBAAkBwB,GAGzBrC,KAAKwD,aAAezB,EACpB/B,KAAKkB,iBAAkB,EACvBlB,KAAKyD,OAAS,IAAIC,WAAS,CAAEJ,YAAavB,EAAMuB,YAAazD,eACvDG,KAAK2D,6BACX3D,KAAKoB,QAAS,EACTpB,KAAK4D,yBAENjB,GACF3C,KAAKU,cAET,MACEV,KAAKkB,gBAAiC,QAAfa,EAAMjC,KAC7BE,KAAKyD,OAAS1B,QACR/B,KAAK6D,6BACX7D,KAAKoB,QAAS,EACTpB,KAAK4D,wBACZ,GAEJ,CAEA,WAAaE,GACX,OAAO9D,KAAKG,QACd,CAEA,YAAa4D,CAAOC,EAAavE,EAAiC,IAChE,MAAMiC,EAAsB,GAU5B,GARK3B,EAAAA,SAASiE,IACZtC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,gDAGvBF,EAAAA,cAAclC,IACjBiC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,0DAGxBH,EAAOS,OAAS,EAClB,MAAM,IAAIC,EAAAA,aAAa,oDAAqDV,GAG9E,OAAO1B,KAAKiE,QAAQD,EAAKvE,EAC3B,CAEA,WAAIyE,GACF,OAAOlE,KAAKc,QACd,CAEA,aAAaqD,CAAWC,GACtB,GAAIA,IAASC,UAAQD,GACnB,MAAM,IAAIvC,EAAAA,UAAU,gDAKtB,aAFsB7B,KAAKsE,SAAYF,IAExBG,MAAK,EAAEvF,IAAKC,KACrBD,EAAIC,GACC,EAGLD,EAAIC,EACC,EAGF,GAEX,CAEA,YAAauF,CAAU/E,EAAyB,IAC9C,MAAMiC,EAAsB,GAU5B,GARKC,EAAAA,cAAclC,IACjBiC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,2DAGxBpC,EAAQ2E,OAASC,EAAAA,QAAQ5E,EAAQ2E,OACnC1C,EAAOE,KAAK,IAAIC,EAAAA,UAAU,yDAGxBH,EAAOS,OAAS,EAClB,MAAM,IAAIC,EAAAA,aAAa,oDAAqDV,GAG9E,MAAMyC,QAAEA,EAAOM,SAAEA,SAAmBzE,KAAK0E,QAAWjF,GAEpD,MAAO,CACL0E,QAASA,EAAQI,MAAK,EAAEvF,IAAKC,KACvBD,EAAIC,GACC,EAGLD,EAAIC,EACC,EAGF,IAETwF,SAAUA,EAASF,MAAK,CAACvF,EAAGC,IACtBD,EAAEgF,IAAM/E,EAAE+E,KACL,EAGLhF,EAAEgF,IAAM/E,EAAE+E,IACL,EAGF,IAGb,CAEA,SAAaW,CAAOX,EAAavE,EAAiC,IAChE,MAAMiC,EAAsB,GAU5B,GARK3B,EAAAA,SAASiE,IACZtC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,gDAGvBF,EAAAA,cAAclC,IACjBiC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,0DAGxBH,EAAOS,OAAS,EAClB,MAAM,IAAIC,EAAAA,aAAa,iDAAkDV,GAG3E,OAAO1B,KAAK4E,KAAQZ,EAAKvE,EAC3B,CAEOoF,gBAAAA,CAAiBC,EAAgBrF,EAAiC,IACvE,MAAMuE,EAAMvE,EAAQsF,QAAUC,EAAAA,IAAIC,QAAQH,GAAUA,EACpD,OAAO9E,KAAKkF,kBAAkBlB,EAChC,CAEA,SAAamB,CACXnB,EACAvE,EAA0D,IAE1D,MAAMiC,EAAsB,GAU5B,GARK3B,EAAAA,SAASiE,IACZtC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,gDAGvBF,EAAAA,cAAclC,IACjBiC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,uDAGxBH,EAAOS,OAAS,EAClB,MAAM,IAAIC,EAAAA,aAAa,iDAAkDV,GAG3E,OAAO1B,KAAKoF,KAAKpB,EAAKvE,EACxB,CAEA,YAAa4F,CAAO5F,GAClB,IAAKkC,EAAAA,cAAclC,GACjB,MAAM,IAAIoC,EAAAA,UAAU,yDAGtB,MAAMsC,QAAEA,EAAOM,SAAEA,GAAahF,EACxBiC,EAAsB,GAU5B,GARK2C,EAAAA,QAAQF,IACXzC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,oDAGvBwC,EAAAA,QAAQI,IACX/C,EAAOE,KAAK,IAAIC,EAAAA,UAAU,qDAGxBH,EAAOS,OAAS,EAClB,MAAM,IAAIC,EAAAA,aAAa,iDAAkDV,GAG3E,OAAO1B,KAAKsF,QAAQ7F,EACtB,CAEA,YAAIgF,GACF,OAAOzE,KAAKiB,SACd,CAEA,QAAIpB,GACF,OAAOG,KAAKC,KACd,CAEA,UAAIuC,GACF,OAAOxC,KAAKK,OACd,CAEA,SAAakF,CAAIvB,EAAawB,EAAgB/F,EAAsB,CAAA,GAClE,MAAMiC,EAAsB,GAc5B,GAZK3B,EAAAA,SAASiE,IACZtC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,gDAGvBF,EAAAA,cAAclC,IACjBiC,EAAOE,KAAK,IAAIC,EAAAA,UAAU,0DAGvB4D,EAAAA,YAAYD,IACf9D,EAAOE,KAAK,IAAIC,EAAAA,UAAU,2DAGxBH,EAAOS,OAAS,EAClB,MAAM,IAAIC,EAAAA,aAAa,iDAAkDV,GAK3E,OAAO1B,KAAK0F,KAAK1B,EAAKwB,EAAoB/F,EAC5C,CAEA,UAAaF,GACX,OAAOS,KAAK2F,OACd,CAEOhD,WAAAA,GACL3C,KAAKU,cACP,CAEOkF,UAAAA,GACL5F,KAAKY,aACP,CAEA,aAAIiF,GACF,OAAO7F,KAAKyD,QAAQ3D,MAAQ,MAC9B,CAEA,QAAIA,GACF,OAAOE,KAAKE,KACd,CAEA,gBAAI4F,GACF,OAAO9F,KAAKsB,aACd,CAEQ2B,4BAAAA,GACN8C,EAAAA,SAASC,GAAGC,EAAAA,UAAUC,MAAOlG,KAAKJ,mBAClCmG,EAAAA,SAASC,GAAGC,EAAAA,UAAUE,aAAcnG,KAAKI,yBACzC2F,EAAAA,SAASC,GAAGC,EAAAA,UAAUG,YAAapG,KAAKO,wBACxCwF,EAAAA,SAASC,GAAGC,EAAAA,UAAUI,aAAcrG,KAAKS,yBACzCsF,EAAAA,SAASC,GAAGC,EAAAA,UAAUK,YAAatG,KAAKW,uBAC1C,CAEA,kBAAc4F,CACZvC,EACAzE,EACAiH,EACAC,EACAC,GAiBA,OAfA1G,KAAKiB,UAAUW,KAAK,CAClBzC,cAAe,EACfG,MAAOqH,KAAKC,MACZJ,eACAE,aACA1C,MACA5E,aAAcuH,KAAKC,MACnBvH,YAAasH,KAAKC,MAClBrH,OACAsH,KAAMJ,EAAM,CAACA,GAAO,GACpBK,aAAc,IAGhB9G,KAAK+G,gBACL/G,KAAKgH,kBACEhH,KAAKiH,iBACd,CAEQC,kBAAAA,CAAsBC,KAA2BC,GACvD,OAAO,IAAIlE,SAASC,IAClBnD,KAAKqB,cAAcO,KAAK,CAACuB,EAASgE,EAAYC,GAAQ,GAE1D,CAEA,qBAAcH,GACZ,IAAKjH,KAAKyD,SAAWzD,KAAKkB,gBACxB,OAKF,OAFclB,KAAKwD,cAAgBxD,KAAKyD,QAE3B8B,IACXU,EAAAA,UAAUoB,SAGVC,kBAAgBC,EAAAA,kBAAkBvH,KAAKiB,WAAyBjB,KAAKuB,iBAAkBvB,KAAK8C,mBAEhG,CAEA,gCAAca,GACZ,IAAM3D,KAAKwD,eAAgBxD,KAAKyD,OAC9B,MAAM,IAAI+D,EAAAA,cACR,2GAIJxH,KAAKiB,UAAY,GACjB,MAAMwG,QAAuBzH,KAAKwD,aAAamB,IAAIsB,EAAAA,UAAUoB,UAE7D,GAAII,EAAgB,CAClB,MAAMhD,EAAWiD,EAAAA,gBACfD,EACAzH,KAAKuB,iBACLvB,KAAK8C,mBAGP,GAAI2B,EAAStC,OAAS,EAAG,CACvB,MAAMiC,EAAOK,EAASkD,KAAIC,GAASA,EAAM5D,YACnChE,KAAKyD,OAAO4B,aAAarF,KAAKwD,aAAaW,QAAQC,IACzDpE,KAAKiB,UAAY4G,EAAAA,kBAAkBpD,EACrC,CACF,CACF,CAEQqD,mBAAAA,GACN,MAAMC,EAAgBC,KAAKC,MAA0B,GAApBjI,KAAKgB,cACtC,IACIkH,EADAC,EAAY,EAGhB,IAAK,IAAIjJ,EAAQc,KAAKiB,UAAUkB,OAAS,EAAGjD,GAAS,EAAGA,GAAS,EAK/D,GAFAiJ,GAAanI,KAAKiB,UAAU/B,GAAQK,KAEhC4I,EAAYJ,EAAe,CAC7BG,EAAQhJ,EACR,KACF,CAGF,OAAOgJ,CACT,CAEQE,WAAAA,CAAY3B,GAClB,IAAK,MAAMmB,KAAS5H,KAAKiB,UACnB2G,EAAMf,KAAKwB,SAAS5B,KACtBmB,EAAMf,KAAOe,EAAMf,KAAKyB,QAAOC,GAAKA,IAAM9B,IAGhD,CAEA,YAActG,GACZ,OAAKH,KAAKoB,QAAWpB,KAAKyD,cAIpBzD,KAAKyD,OAAOK,QAClB9D,KAAKiB,UAAY,GACjBjB,KAAKmB,YAAc,GACnBnB,KAAKgH,kBACEhH,KAAKiH,mBAPHjH,KAAKkH,mBAAmBjB,EAAAA,UAAUC,MAQ7C,CAEA,aAAcjC,CAAQD,EAAavE,EAAiC,IAClE,IAAKO,KAAKoB,SAAWpB,KAAKyD,OACxB,OAAOzD,KAAKkH,mBAAmBjB,EAAAA,UAAUuC,OAAQxE,EAAKvE,GAGxD,MAAMgJ,EAAYhJ,EAAQsF,QAAUC,EAAAA,IAAIC,QAAQjB,GAAOA,EAGvD,cAFsBhE,KAAKyD,OAAOM,OAAO0E,WAMnCzI,KAAK0I,gBAAgBD,IACpB,EACT,CAEA,qBAAcC,CAAgB1E,GAC5B,MAAM9E,EAAQc,KAAKiB,UAAU0H,WAAUlE,GAAYA,EAAST,MAAQA,IAEpE,IAAc,IAAV9E,EAOJ,OAHAc,KAAKiB,UAAU2H,OAAO1J,EAAO,GAC7Bc,KAAK+G,gBACL/G,KAAKgH,kBACEhH,KAAKiH,iBACd,CAEA,cAAc3C,CAAYF,GACxB,IAAKpE,KAAKoB,SAAWpB,KAAKyD,OACxB,OAAOzD,KAAKkH,mBAAmBjB,YAAU4C,QAASzE,GAGpD,MAAM0E,EAAY1E,GAAQpE,KAAKiB,UAAU0G,KAAIlD,GAAYA,EAAST,MAElE,aADsBhE,KAAKyD,OAAOU,QAAQ2E,IAC3BnB,KAAI,EAAE3D,EAAK+E,KAAU,CAAC/E,EAAK0D,EAAAA,gBAAgBqB,EAAM/I,KAAKuB,iBAAkBvB,KAAK8C,qBAC9F,CAEA,aAAc4B,EAAWsE,WAAEA,EAAUC,cAAEA,EAAa7E,KAAEA,EAAIqC,IAAEA,IAC1D,IAAIyC,EACAzE,EAAW,IAAIzE,KAAKiB,WAEpBwF,GACFhC,EAAWzE,KAAKiB,UAAUqH,QAAOa,GAAQA,EAAKtC,KAAKwB,SAAS5B,KAC5DyC,EAAazE,EAASkD,KAAIwB,GAAQA,EAAKnF,MAEnCgF,GACFhJ,KAAKoI,YAAY3B,IAEVrC,IACTK,EAAWzE,KAAKiB,UAAUqH,QAAOa,GAAQ/E,EAAKiE,SAASc,EAAKnF,OAC5DkF,EAAa9E,GAGf,IAAID,QAAgBnE,KAAKsE,SAAY4E,GAErC,GAAID,EAAe,CACjB,MAAMG,EAAoBC,EAAAA,UAAUJ,GAEpC9E,EAAUA,EAAQmE,QAAO,EAAC,CAAGS,KAC3BK,EAAkBE,OAAM,EAAGC,aAAYC,cAAe7E,EAAAA,IAAIoE,EAAMS,KAAcD,MAGhF9E,EAAWA,EAAS6D,QAAOa,GAAQhF,EAAQsF,MAAK,EAAEzF,KAASA,IAAQmF,EAAKnF,OAC1E,CAEA,MAAO,CAAEG,UAASM,WACpB,CAEA,UAAcG,CAAQZ,EAAavE,GACjC,IAAKO,KAAKoB,SAAWpB,KAAKyD,OACxB,OAAOzD,KAAKkH,mBAAmBjB,EAAAA,UAAUyD,IAAK1F,EAAKvE,GAGrD,MAAMkK,EAASlK,EAAQsF,QAAUC,EAAAA,IAAIC,QAAQjB,GAAOA,EAGpD,GAFmBhE,KAAK4J,sBAAsBD,GAO5C,YAJIlK,EAAQoK,qBACJ7J,KAAKiE,QAAQ0F,IAMvB,MAAMnE,QAAcxF,KAAKyD,OAAOkB,IAAIgF,GAEpC,OAAKnE,SAICxF,KAAK8J,gBAAgBH,GACpBjC,EAAAA,gBAAgBlC,EAAOxF,KAAKuB,iBAAkBvB,KAAK8C,yBAL1D,CAMF,CAEQiH,gBAAAA,CAAiB/F,GACvB,MAAMS,EAAWzE,KAAKkF,kBAAkBlB,GACxC,OAAOS,EAAWA,EAAS+B,kBAAewD,CAC5C,CAEQ9E,iBAAAA,CAAkBlB,GACxB,OAAOhE,KAAKiB,UAAUgJ,MAAKxF,GAAYA,EAAST,MAAQA,GAC1D,CAEA,UAAcoB,CACZpB,EACAvE,GAEA,IAAKO,KAAKoB,SAAWpB,KAAKyD,OACxB,OAAOzD,KAAKkH,mBAAmBjB,EAAAA,UAAUiE,IAAKlG,EAAKvE,GAGrD,MAAM0K,EAAS1K,EAAQsF,QAAUC,EAAAA,IAAIC,QAAQjB,GAAOA,EAGpD,GAFmBhE,KAAK4J,sBAAsBO,GAO5C,OAJI1K,EAAQoK,qBACJ7J,KAAKiE,QAAQkG,IAGd,EAKT,cAFqBnK,KAAKyD,OAAO0B,IAAIgF,KAM9BnK,KAAK+J,iBAAiBI,KAAW,EAC1C,CAEQP,qBAAAA,CAAsB5F,GAC5B,GAAIhE,KAAK6C,0BACP,OAAO,EAGT,MAAM2D,EAAexG,KAAK+J,iBAAiB/F,GAC3C,QAAOwC,IAAgBA,EAAa4D,UACtC,CAEA,aAAc9E,CAAQ7F,GACpB,IAAKO,KAAKoB,SAAWpB,KAAKyD,OACxB,OAAOzD,KAAKkH,mBAAmBjB,YAAUoE,OAAQ5K,GAGnD,IAAI6K,EAAuB,GAEvBtK,KAAKiB,UAAUkB,OAAS,IAC1BmI,EAAWtK,KAAKiB,UAAUqH,QAAO7D,IACvBhF,EAAQgF,SAASgF,MAAKc,GAAmB9F,EAAST,MAAQuG,EAAgBvG,SAItF,MAAMG,EAAU1E,EAAQ0E,QAAQwD,KAG9B,EAAE3D,EAAK+E,KAAU,CAAC/E,EAAKsD,EAAAA,gBAAgByB,EAAM/I,KAAKuB,iBAAkBvB,KAAK8C,4BAGrE9C,KAAKyD,OAAO4B,OAAOlB,GACzBnE,KAAKiB,UAAY4G,oBAAkB,IAAIyC,KAAa7K,EAAQgF,WAC5DzE,KAAK+G,sBACC/G,KAAKiH,kBACXjH,KAAKgH,iBACP,CAEQjE,iBAAAA,CAAkByH,GACxB,OAAOA,EAAW,CAChBC,eAAgBpH,MAAOW,EAAa6C,KAClC7G,KAAKkE,QAAQwG,KAAK1K,KAAKN,OAAOC,cAAe,CAAEgL,cAAe3K,KAAKiE,QAAQD,GAAMA,MAAK6C,QAAK,EAE7F+D,iBAAkB,IAAM5K,KAAKiB,WAEjC,CAEQ4J,UAAAA,CAAW7G,GACjBhE,KAAKmB,YAAcnB,KAAKmB,YAAYmH,QAAO9C,GAASA,IAAUxB,GAChE,CAEQ8G,eAAAA,GACN,MAAM5L,EAAQc,KAAK8H,sBAEd5I,GAAUc,KAAKK,SAIfL,KAAKK,QAAQ0K,KAAK/K,KAAKiB,UAAU+J,MAAM9L,GAC9C,CAEA,4BAAc0E,GACZ,IAAK,MAAOT,EAASgE,EAAYC,KAAYpH,KAAKqB,cAEhD8B,QAAcnD,KAAKmH,MAAeC,IAGpCpH,KAAKqB,cAAgB,EACvB,CAEA,gCAAcwC,GACZ,IAAK7D,KAAKyD,SAAWzD,KAAKkB,gBACxB,OAGF,MAAMuD,QAAiBzE,KAAKyD,OAAOkB,IAAIsB,EAAAA,UAAUoB,UAE7C5C,IACFzE,KAAKiB,UAAY4G,EAAAA,kBAAkBH,kBAAgBjD,EAAUzE,KAAKuB,iBAAkBvB,KAAK8C,oBAE7F,CAEA,UAAc4C,CAAK1B,EAAawB,EAAkB/F,GAChD,IAAKO,KAAKoB,SAAWpB,KAAKyD,OACxB,OAAOzD,KAAKkH,mBAAmBjB,EAAAA,UAAUgF,IAAKjH,EAAKwB,EAAO/F,GAG5D,MAAM+G,EAAe,IAAI0E,eAAazL,EAAQ0L,eACxCC,aAAEA,GAAiB5E,EAAa/B,SAEtC,GAAI2G,EAAaC,SAAYrL,KAAKgD,cAAgBoI,EAAaE,QAC7D,OAGF,MAAMC,EAAS9L,EAAQsF,QAAUC,EAAAA,IAAIC,QAAQjB,GAAOA,EAC9CwH,EAAaxL,KAAKmB,YAAYkH,SAASkD,GAExCC,GACHxL,KAAKmB,YAAYS,KAAK2J,GAGxB,IACE,MAAME,QAAgBzL,KAAKyD,OAAO0B,IAAIoG,IAAYC,EAC5CE,EAAmBpE,EAAAA,gBAAgB9B,EAAOxF,KAAKuB,iBAAkBvB,KAAK8C,yBACtE9C,KAAKyD,OAAO8B,IAAIgG,EAAQG,SAEvBD,EACHzL,KAAK8J,gBAAgByB,EAAQI,EAAAA,OAAOD,GAAmBlF,EAAc/G,EAAQgH,IAAKhH,EAAQiH,YAC1F1G,KAAKuG,aAAagF,EAAQI,EAAAA,OAAOD,GAAmBlF,EAAc/G,EAAQgH,IAAKhH,EAAQiH,aAE3F1G,KAAK6K,WAAWU,EAClB,CAAE,MAAOK,GAEP,MADA5L,KAAK6K,WAAWU,GACVK,CACR,CACF,CAEA,WAAcjG,GACZ,OAAK3F,KAAKoB,QAAWpB,KAAKyD,OAInBzD,KAAKyD,OAAOlE,OAHVS,KAAKkH,mBAAmBjB,EAAAA,UAAU4F,KAI7C,CAEQ9E,aAAAA,GACN/G,KAAKiB,UAAUsD,KAAKzF,EAAKC,gBAC3B,CAEQ2B,YAAAA,GACNV,KAAK8L,kBAAoBC,aAAY,KAC9B/L,KAAKgM,4BAA0B,GACnChM,KAAKa,gBACV,CAEQD,WAAAA,GACFZ,KAAK8L,mBACPG,cAAcjM,KAAK8L,kBAEvB,CAEA,gCAAcE,GACZ,IAAMhM,KAAKwD,eAAgBxD,KAAKyD,OAC9B,OAGF,MAAMW,EAAOpE,KAAKiB,UAAU0G,KAAIC,GAASA,EAAM5D,MAC1ChE,KAAKwD,aAAa6B,aAAarF,KAAKyD,OAAOU,QAAQC,GAC1D,CAEQ4C,eAAAA,GACNhH,KAAKsB,cAAgBtB,KAAKiB,UAAUiL,QAAO,CAACC,EAAK3G,IAAU2G,EAAM3G,EAAMjG,MAAM,IAExES,KAAK6C,2BAA6B7C,KAAKsB,cAAgBtB,KAAKgB,cAC/DhB,KAAK8K,iBAET,CAEA,qBAAchB,CACZ9F,EACAzE,EACAiH,EACAC,EACAC,GAEA,MAAMkB,EAAQ5H,KAAKkF,kBAAkBlB,GAErC,GAAK4D,EA2BL,OAvBIrI,GACFqI,EAAMrI,KAAOA,EACbqI,EAAMvI,YAAcsH,KAAKC,MACzBgB,EAAMd,cAAgB,IAEtBc,EAAMzI,eAAiB,EACvByI,EAAMxI,aAAeuH,KAAKC,OAGxBJ,IACFoB,EAAMpB,aAAeA,GAGlB4F,EAAAA,YAAY3F,IACfmB,EAAMf,KAAKjF,KAAK6E,GAGdC,IACFkB,EAAMlB,WAAa2F,OAAOC,OAAO1E,EAAMlB,YAAc,CAAA,EAAIA,IAG3D1G,KAAK+G,gBACL/G,KAAKgH,kBACEhH,KAAKiH,iBACd"}