Skip to content
Snippets Groups Projects
Commit 4435e282 authored by julian.baeume's avatar julian.baeume :pick:
Browse files

add first dedicated metrics to analyse cache behaviour

this should help to get insights about how the caches are filled locally
parent 20c4e7bb
No related branches found
No related tags found
No related merge requests found
......@@ -7,12 +7,19 @@ import { NotFoundError } from './errors.js'
import * as redis from './redis.js'
import zlib from 'node:zlib'
import { promisify } from 'node:util'
import { Gauge } from 'prom-client'
const gzip = promisify(zlib.gzip)
const compressFileSize = Number(process.env.COMPRESS_FILE_SIZE)
const compressionMimeTypes = (process.env.COMPRESS_FILE_TYPES || '').replace(/([.+*?^$()[\]{}|])/g, '\\$1').split(' ')
const compressionWhitelistRegex = new RegExp(`^(${compressionMimeTypes.join('|')})($|;)`, 'i')
export const fileCacheSizeGauge = new Gauge({
name: 'file_cache_size',
help: 'Number of entries in file cache'
})
export function createWritable (body) {
if (typeof body !== 'string' && !(body instanceof Buffer)) return JSON.stringify(body)
return body
......@@ -96,6 +103,7 @@ export function getFile ({ version, path }) {
if (body) {
logger.debug(`[Files] Resolve from redis: ${key}`)
fileCacheSizeGauge.inc()
return (cache.getCache()[key] = { body, ...JSON.parse(meta) })
}
}
......@@ -113,6 +121,7 @@ export function getFile ({ version, path }) {
// overwrite cache with synchronous data
logger.debug(`[Files] Store in memory: ${key}`)
fileCacheSizeGauge.inc()
return (cache.getCache()[key] = dataFromServer)
})()
......
......@@ -27,7 +27,7 @@ export async function fetchViteManifests () {
return viteManifests.reduce((memo, manifest) => Object.assign(memo, manifest), {})
}
export function getViteManifests ({ version }) {
export async function getViteManifests ({ version }) {
return cache.get(getRedisKey({ version, name: 'viteManifests' }), () => fetchViteManifests())
}
......
......@@ -3,9 +3,27 @@ import { getRedisKey, hash } from './util.js'
import { logger } from './logger.js'
import * as cache from './cache.js'
import * as redis from './redis.js'
import { Gauge } from 'prom-client'
import { getViteManifests } from './manifests.js'
let latestVersion
const manifestFileEntriesGauge = new Gauge({
name: 'manifest_file_entries',
help: 'Number of entries in merged vite manifest (number of all known files)',
async collect () {
const version = latestVersion
this.set({ version }, Object.keys(await getViteManifests({ version })).length)
},
labelNames: ['version']
})
const versionUpdateGauge = new Gauge({
name: 'version_update_event',
help: 'Timestamp of a version update event',
labelNames: ['version']
})
export const fetchLatestVersion = async () => {
const infos = await Promise.all(configMap.urls.map(async baseUrl => {
try {
......@@ -36,6 +54,7 @@ export async function getLatestVersion () {
const version = await redis.client.get(getRedisKey({ name: 'latestVersion' }))
if (version) {
logger.info(`[Version] Got initial version from redis: '${version}'`)
versionUpdateGauge.setToCurrentTime({ version })
return (latestVersion = version)
}
}
......@@ -61,6 +80,7 @@ export function registerLatestVersionListener (client) {
if (channel !== key) return
logger.info(`[Version] Received 'updateLatestVersion' event. Clearing cache. New version: '${version}'`)
await configMap.load()
versionUpdateGauge.setToCurrentTime({ version })
cache.clear()
latestVersion = version
})
......@@ -73,6 +93,12 @@ export async function updateVersionProcessor () {
getLatestVersion(),
fetchLatestVersion()
])
// don't wait for the data, can be done in background
getViteManifests({ fetchedVersion }).then(manifests => {
manifestFileEntriesGauge.set({ version: fetchedVersion }, Object.keys(manifests).length)
})
if (storedVersion === fetchedVersion) {
logger.info(`[Version] No new version has been found. No update needed. Current version: ${storedVersion}`)
return fetchedVersion
......@@ -91,6 +117,7 @@ export async function updateVersionProcessor () {
await redis.client.set(getRedisKey({ name: 'prevProcessedVersion' }), fetchedVersion)
}
} else {
versionUpdateGauge.setToCurrentTime({ version: latestVersion })
// if redis is disabled, this will only be trigger by a setInterval and not from a redis event
logger.info('[Version] Clear local cache due to version update.')
cache.clear()
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment