local Cache = {} local Config = require("lib/settings/clientConfig.lua") local max = 5000 local CreateThread = CreateThread local Wait = Wait local GetGameTimer = GetGameTimer Cache.Caches = Cache.Caches or {} Cache.LoopRunning = Cache.LoopRunning or false local function print(...) if Config.Debug then print("^2[Cache]^0", ...) end end local function StartLoop() if Cache.LoopRunning then return end Cache.LoopRunning = true CreateThread(function() while Cache.LoopRunning do local now = GetGameTimer() local minWait = nil local caches = Cache.Caches for name, cache in pairs(caches) do if cache.Compare then cache.LastChecked = cache.LastChecked or now cache.WaitTime = cache.WaitTime or max local elapsed = now - cache.LastChecked local remaining = cache.WaitTime - elapsed if remaining <= 0 then local oldValue = cache.Value cache.Value = cache.Compare() if cache.Value ~= oldValue and cache.OnChange then for _, onChange in pairs(cache.OnChange) do onChange(cache.Value, oldValue) end end cache.LastChecked = now remaining = cache.WaitTime end if not minWait or remaining < minWait then minWait = remaining if minWait <= 0 then break end end end end if minWait then Wait(math.max(0, minWait)) else Wait(max) end end end) end function Cache.Create(name, compare, waitTime) assert(name, "Cache name is required.") assert(compare, "Comparison function is required.") assert(type(compare) == "function", "Comparison function must be a function.") local _name = tostring(name) -- Ensure name is a string local cache = Cache.Caches[_name] if cache and cache.Compare == compare then print(name .. " already exists with the same comparison function.") return cache end cache = nil -- clean variable, so we can use the same name for the new cache local s, r = pcall(function() -- Try to create the cache and catch any errors local _cache = { Name = _name, Compare = compare, WaitTime = waitTime or max, LastChecked = nil, OnChange = {}, Value = compare() } Cache.Caches[_name] = _cache print(_name .. " created with initial value: " .. tostring(Cache.Caches[_name].Value)) for _, onChange in pairs(_cache.OnChange) do onChange(_cache.Value, nil) end end) if not s then print("Error creating cache '" .. _name .. "': " .. tostring(r)) return nil end return StartLoop() end function Cache.Get(name) assert(name, "Cache name is required.") local _name = tostring(name) local cache = Cache.Caches[_name] return cache and cache.Value or nil end function Cache.OnChange(name, onChange) assert(name, "Cache name is required.") local _name = tostring(name) -- Ensure name is a string local cache = Cache.Caches[_name] assert(cache, "Cache with name '" .. _name .. "' does not exist.") cache.OnChange[#cache.OnChange + 1] = onChange end function Cache.Remove(name) assert(name, "Cache name is required.") local _name = tostring(name) -- Ensure name is a string local cache = Cache.Caches[_name] if cache then Cache.Caches[_name] = nil print(_name .. " removed from cache.") if next(Cache.Caches) == nil then Cache.LoopRunning = false -- Stop the loop if no caches are left end end end return Cache