mirror of
https://github.com/SukkaW/Surge.git
synced 2025-12-12 01:00:34 +08:00
Refactor fs memo cache
This commit is contained in:
parent
8e96c36ea0
commit
84bdc48a72
@ -44,12 +44,17 @@ export type FsMemoCacheOptions<T> = CacheApplyOption<T, string> & {
|
||||
ttl?: undefined | never
|
||||
};
|
||||
|
||||
export function cache<Args extends Devalue[], T>(
|
||||
function createCache(onlyUseCachedIfFail: boolean) {
|
||||
return function cache<Args extends Devalue[], T>(
|
||||
fn: (...args: Args) => Promise<T>,
|
||||
opt: FsMemoCacheOptions<T>
|
||||
): (...args: Args) => Promise<T> {
|
||||
const fixedKey = fn.toString();
|
||||
|
||||
if (opt.temporaryBypass) {
|
||||
return fn;
|
||||
}
|
||||
|
||||
return async function cachedCb(...args: Args) {
|
||||
const { stringify: devalueStringify } = await import('devalue');
|
||||
|
||||
@ -60,76 +65,52 @@ export function cache<Args extends Devalue[], T>(
|
||||
xxhash64(devalueStringify(args))
|
||||
])).join('|');
|
||||
|
||||
const cacheName = fn.name || fixedKey;
|
||||
|
||||
if (opt.temporaryBypass) {
|
||||
return fn(...args);
|
||||
}
|
||||
const cacheName = picocolors.gray(fn.name || fixedKey || cacheKey);
|
||||
|
||||
const cached = fsMemoCache.get(cacheKey);
|
||||
if (cached == null) {
|
||||
console.log(picocolors.yellow('[cache] miss'), picocolors.gray(cacheName || cacheKey));
|
||||
|
||||
const serializer = 'serializer' in opt ? opt.serializer : identity as any;
|
||||
|
||||
const value = await fn(...args);
|
||||
|
||||
fsMemoCache.set(cacheKey, serializer(value), TTL);
|
||||
return value;
|
||||
}
|
||||
|
||||
console.log(picocolors.green('[cache] hit'), picocolors.gray(cacheName || cacheKey));
|
||||
|
||||
fsMemoCache.updateTtl(cacheKey, TTL);
|
||||
|
||||
const deserializer = 'deserializer' in opt ? opt.deserializer : identity as any;
|
||||
return deserializer(cached);
|
||||
};
|
||||
}
|
||||
|
||||
export function cachedOnlyFail<Args extends Devalue[], T>(
|
||||
fn: (...args: Args) => Promise<T>,
|
||||
opt: FsMemoCacheOptions<T>
|
||||
): (...args: Args) => Promise<T> {
|
||||
const fixedKey = fn.toString();
|
||||
|
||||
return async function cachedCb(...args: Args) {
|
||||
const { stringify: devalueStringify } = await import('devalue');
|
||||
|
||||
// Construct the complete cache key for this function invocation
|
||||
// typeson.stringify is still limited. For now we uses typescript to guard the args.
|
||||
const cacheKey = (await Promise.all([
|
||||
xxhash64(fixedKey),
|
||||
xxhash64(devalueStringify(args))
|
||||
])).join('|');
|
||||
|
||||
const cacheName = fn.name || fixedKey;
|
||||
|
||||
if (opt.temporaryBypass) {
|
||||
return fn(...args);
|
||||
}
|
||||
|
||||
const cached = fsMemoCache.get(cacheKey);
|
||||
|
||||
if (onlyUseCachedIfFail) {
|
||||
try {
|
||||
const value = await fn(...args);
|
||||
|
||||
const serializer = 'serializer' in opt ? opt.serializer : identity as any;
|
||||
console.log(picocolors.gray('[cache] update'), cacheName);
|
||||
fsMemoCache.set(cacheKey, serializer(value), TTL);
|
||||
|
||||
return value;
|
||||
} catch (e) {
|
||||
if (cached == null) {
|
||||
console.log(picocolors.red('[fail] and no cache, throwing'), picocolors.gray(cacheName || cacheKey));
|
||||
console.log(picocolors.red('[fail] and no cache, throwing'), cacheName);
|
||||
throw e;
|
||||
}
|
||||
|
||||
fsMemoCache.updateTtl(cacheKey, TTL);
|
||||
|
||||
console.log(picocolors.yellow('[fail] try cache'), picocolors.gray(cacheName || cacheKey));
|
||||
const deserializer = 'deserializer' in opt ? opt.deserializer : identity as any;
|
||||
console.log(picocolors.yellow('[fail] try cache'), cacheName);
|
||||
|
||||
return deserializer(cached);
|
||||
}
|
||||
} else {
|
||||
if (cached == null) {
|
||||
console.log(picocolors.yellow('[cache] miss'), cacheName);
|
||||
|
||||
const value = await fn(...args);
|
||||
|
||||
fsMemoCache.set(cacheKey, serializer(value), TTL);
|
||||
return value;
|
||||
}
|
||||
|
||||
console.log(picocolors.green('[cache] hit'), cacheName);
|
||||
|
||||
fsMemoCache.updateTtl(cacheKey, TTL);
|
||||
|
||||
return deserializer(cached);
|
||||
}
|
||||
};
|
||||
};
|
||||
}
|
||||
|
||||
export const cache = createCache(false);
|
||||
export const cachedOnlyFail = createCache(true);
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user