@graphql-mesh/cache-inmemory-lru
Version:
58 lines (57 loc) • 1.86 kB
JavaScript
import { toMeshPubSub, } from '@graphql-mesh/types';
import { createLruCache } from '@graphql-mesh/utils';
import { DisposableSymbols } from '@whatwg-node/disposablestack';
export default class InMemoryLRUCache {
constructor(options) {
this.timeouts = new Map();
this.lru = createLruCache(options?.max, options?.ttl);
const pubsub = toMeshPubSub(options?.pubsub);
const subId = pubsub?.subscribe?.('destroy', () => {
pubsub.unsubscribe(subId);
this[DisposableSymbols.dispose]();
});
}
get(key) {
return this.lru.get(key);
}
set(key, value, options) {
this.lru.set(key, value);
if (options?.ttl && options.ttl > 0) {
const timeout = setTimeout(() => {
this.timeouts.delete(key);
this.lru.delete(key);
}, options.ttl * 1000);
const existingTimeout = this.timeouts.get(key);
if (existingTimeout) {
// we debounce the timeout because we dont want to "pull the rug" from a "parallel" get
clearTimeout(existingTimeout);
}
this.timeouts.set(key, timeout);
}
}
delete(key) {
try {
this.lru.delete(key);
return true;
}
catch (e) {
return false;
}
}
getKeysByPrefix(prefix) {
const keysWithPrefix = [];
for (const key of this.lru.keys()) {
if (key.startsWith(prefix)) {
keysWithPrefix.push(key);
}
}
return keysWithPrefix;
}
[DisposableSymbols.dispose]() {
// clear all timeouts and then empty the map
for (const timeout of this.timeouts.values()) {
clearTimeout(timeout);
}
this.timeouts.clear();
}
}