Files
All-in-one-Financial-Analysis/atlas-terminal/server/services/cache.py
T

41 lines
1.0 KiB
Python
Raw Normal View History

"""Simple in-memory TTL cache for expensive macro data fetches."""
from __future__ import annotations
import time
import threading
from typing import Any, Callable, TypeVar
_lock = threading.Lock()
_store: dict[str, tuple[float, Any]] = {}
F = TypeVar("F", bound=Callable)
def cached(key: str, ttl_seconds: int = 3600):
"""Decorator that caches a function result for *ttl_seconds*."""
def decorator(fn: Callable) -> Callable:
def wrapper(*args: Any, **kwargs: Any) -> Any:
now = time.time()
with _lock:
if key in _store:
ts, val = _store[key]
if now - ts < ttl_seconds:
return val
result = fn(*args, **kwargs)
with _lock:
_store[key] = (now, result)
return result
return wrapper
return decorator
def invalidate(key: str) -> None:
with _lock:
_store.pop(key, None)
def invalidate_all() -> None:
with _lock:
_store.clear()