fix(manager-core): F-P-009 cache resolved Principals (60s TTL) in auth middleware
attach_principal_if_present runs on every request that carries a Bearer header, including data-plane paths that may not even need authz. Each call paid three DB round-trips on the session path (lookup + admin_users.get + touch) plus an Argon2 verify per prefix-colliding candidate on the API-key path. A hot user with multiple keys serialized every request behind N×Argon2. Add a process-shared PrincipalCache keyed on hash_token(bearer) → (Instant, Principal), TTL 60s. resolve_principal checks the cache first; on miss falls through to the verify_api_key / verify_session path and writes back on success. - Lazy GC: when the cache exceeds 1024 entries, sweep expired before inserting (kept simple — production sees few unique hot tokens). - Cache wired through AuthState; constructed once in picloud/src/lib.rs. - Skip-when-route-doesn't-need-auth scaffolding is deferred to a follow-up — it requires touching the router shape, which is more invasive than the 60s cache alone warrants. AUDIT.md anchor: F-P-009 (cache; skip-path deferred). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -489,6 +489,7 @@ pub async fn build_app(
|
||||
sessions: auth.sessions.clone(),
|
||||
keys: auth.keys.clone(),
|
||||
ttl: auth.ttl,
|
||||
principal_cache: Arc::new(picloud_manager_core::auth_middleware::PrincipalCache::new()),
|
||||
};
|
||||
let admins_state = AdminsState {
|
||||
users: auth.users.clone(),
|
||||
|
||||
Reference in New Issue
Block a user