//! # Requests limit helper //! //! Handle the limitation of requests, depending on threshold criterias use std::sync::{Arc, Mutex}; use crate::constants::LIMIT_COUNTER_LIFETIME; use crate::data::error::ResultBoxError; use crate::utils::date_utils; /// Information about a IP address limitation struct IpInfo { time_start: u64, count: u64, } /// Limits cache type Cache = Arc>; static mut LIMITS_CACHE: Option>> = None; /// Initialize limit cache storage pub fn init() { let limits_cache = Arc::new(dashmap::DashMap::new()); let limits_cache = Some(Arc::new(Mutex::new(limits_cache))); unsafe { LIMITS_CACHE = limits_cache; } } /// Get access to the cache. This resource must absolutely be released as quickly as possible fn get_cache() -> ResultBoxError { let cache: Cache; unsafe { let guard = LIMITS_CACHE.as_ref().unwrap().lock(); cache = guard.unwrap().clone(); } Ok(cache) } /// Clean cached information pub fn clean_cache() -> ResultBoxError { let time = date_utils::time(); let cache = get_cache()?; let obsolete_ips: Vec = cache .iter() .filter(|k| k.time_start + LIMIT_COUNTER_LIFETIME < time) .map(|k| k.key().to_string()) .collect(); for obsolete_ip in obsolete_ips { cache.remove(&obsolete_ip); } Ok(()) }