Skip to main content

rustio_core/auth/
mod.rs

1//! Authentication & authorization.
2//!
3//! Three pieces:
4//! - `users.rs`       — user records, password hashing, login/logout
5//! - `sessions.rs`    — DB-backed sessions with expiry cleanup
6//! - `permissions.rs` — granular permissions + groups + the
7//!   `authorize!` check used throughout the admin
8//!
9//! A user belongs to zero or more groups. Permissions come from two
10//! sources: (a) direct assignments on the user, (b) inherited from
11//! the user's groups. The permission string is
12//! `"<app>.<action>_<model>"` — e.g. `"posts.change_post"`.
13
14mod permissions;
15mod role;
16mod sessions;
17mod users;
18
19pub use permissions::{
20    add_user_to_group, bootstrap_default_groups, check_permission, create_group, grant_to_group,
21    grant_to_user, init_permission_tables, lazy_attach_permissions, permissions_for_user,
22    register_model_permissions, remove_user_from_group, Permission, PermissionError, Superuser,
23};
24pub(crate) use permissions::invalidate_user_cache;
25pub use role::Role;
26pub use sessions::{
27    create_session, delete_session, identity_from_session, init_session_tables,
28    purge_expired_sessions, session_token_from_cookie, SESSION_COOKIE,
29};
30pub use users::{
31    bootstrap_demo_users, create_user, find_user_by_email, hash_password, init_user_tables,
32    load_user_profile, login, migrate_user_schema, set_password, update_user_role, verify_password,
33    would_orphan_developers, Identity, StoredUser, UserProfile,
34};
35
36use crate::error::Result;
37use crate::orm::Db;
38
39/// Shared serialization lock for tests that toggle `RUSTIO_DEMO_MODE`
40/// (or any other process env var). `tokio::test`s run on a thread
41/// pool and `std::env::set_var` mutates process state — without a
42/// process-wide lock, parallel tests stomp each other's env state.
43/// Using `tokio::sync::Mutex` so it can be held across `.await` (the
44/// `await_holding_lock` clippy lint forbids `std::sync::Mutex`).
45#[cfg(test)]
46pub(crate) static TEST_ENV_LOCK: tokio::sync::Mutex<()> =
47    tokio::sync::Mutex::const_new(());
48
49/// Initialise every auth-related table. Safe to call on every boot.
50pub async fn init_tables(db: &Db) -> Result<()> {
51    init_user_tables(db).await?;
52    // Phase 7a/0.5: 5-tier role + demo columns. Idempotent.
53    migrate_user_schema(db).await?;
54    init_session_tables(db).await?;
55    // Phase 10/a: session-level metadata (ip, user_agent). Idempotent.
56    sessions::migrate_session_schema(db).await?;
57    init_permission_tables(db).await?;
58    Ok(())
59}