nuxt-multi-cache
Version:
SSR route, component and data cache for Nuxt.js
89 lines (88 loc) • 2.56 kB
JavaScript
import { getCurrentInstance, useSSRContext } from "vue";
import { logger } from "../helpers/logger.js";
import {
getExpiresValue,
getMultiCacheContext,
getCacheKeyWithPrefix,
isExpired
} from "./../helpers/server.js";
import { useRuntimeConfig } from "#imports";
export function useDataCache(key, providedEvent) {
const dummy = {
addToCache: (_v) => {
return Promise.resolve();
},
cacheTags: []
};
const isServer = import.meta.env.VITEST_SERVER === "true" || import.meta.server;
if (!isServer) {
return Promise.resolve(dummy);
}
const { debug } = useRuntimeConfig().multiCache || {};
try {
const event = (() => {
if (providedEvent) {
return providedEvent;
}
if (!getCurrentInstance()) {
if (debug) {
logger.warn(
"No H3Event provided while not in vue context when calling useDataCache for key: " + key
);
}
return;
}
const ssrContext = useSSRContext();
if (ssrContext) {
return ssrContext.event;
}
})();
const multiCache = getMultiCacheContext(event);
if (!multiCache?.data) {
return Promise.resolve(dummy);
}
const fullKey = getCacheKeyWithPrefix(key, event);
return multiCache.data.getItem(fullKey).then((v) => {
const item = v;
const addToCache = (data, cacheTags = [], maxAge) => {
const item2 = { data, cacheTags };
if (maxAge) {
item2.expires = getExpiresValue(maxAge);
}
if (debug) {
logger.info("Stored item in data cache: " + fullKey);
}
return multiCache.data.setItem(fullKey, item2, { ttl: maxAge });
};
if (item) {
const itemIsExpired = isExpired(item);
if (!itemIsExpired) {
if (debug) {
logger.info("Returned item from data cache: " + fullKey);
}
return {
addToCache,
// Extract the value. If the item was stored along its cache tags, it
// will be an object with a cacheTags property.
value: item.data,
cacheTags: item.cacheTags || [],
expires: item.expires
};
} else if (debug) {
logger.info(
"Skipped returning item from data cache because expired: " + fullKey
);
}
}
return {
addToCache,
cacheTags: []
};
});
} catch (e) {
if (e instanceof Error) {
console.debug(e.message);
}
}
return Promise.resolve(dummy);
}