| Crates.io | authfix |
| lib.rs | authfix |
| version | 0.1.1 |
| created_at | 2025-07-27 15:00:37.198494+00 |
| updated_at | 2025-07-27 16:30:15.128252+00 |
| description | A simple and extensible authentication layer for Actix Web, designed for fast integration and easy configuration. |
| homepage | https://github.com/Hypnagokali/authfix |
| repository | https://github.com/Hypnagokali/authfix |
| max_upload_size | |
| id | 1770145 |
| size | 230,820 |
Authentication layer for Actix-Web
This library offers an authentication middleware for Actix Web. It's easy to use and quick to set up.
Currently it provides session-based authentication built on actix-session, but you can implement your own AuthenticationProvider if needed. A provider for OIDC is planned for v0.2.0.
It supports multi-factor authentication.
Factor trait.Check out the examples repo for detailed and working examples: Authfix examples
use actix_web::{HttpResponse, HttpServer, Responder, cookie::Key, get};
use authfix::{
AuthToken,
login::{LoadUserByCredentials, LoadUserError, LoginToken},
session::{AccountInfo, app_builder::SessionLoginAppBuilder},
};
use serde::{Deserialize, Serialize};
// A user intended for session authentication must derive Serialize, and Deserialize.
#[derive(Serialize, Deserialize)]
struct User {
name: String,
}
// AccountInfo trait is used for disabling the user or to lock the account
// The user is enabled by default
impl AccountInfo for User {}
// Struct that handles the authentication
struct AuthenticationService;
// LoadUsersByCredentials uses async_trait, so its needed when implementing the trait for AuthenticationService
// async_trait is re-exported by authfix.
impl LoadUserByCredentials for AuthenticationService {
type User = User;
async fn load_user(&self, login_token: &LoginToken) -> Result<Self::User, LoadUserError> {
// load user by email logic and check password
// currently authfix does not provide hashing functions, you can use for example https://docs.rs/argon2/latest/argon2/
if login_token.email == "test@example.org" && login_token.password == "password" {
Ok(User {
name: "Johnny".to_owned(),
})
} else {
Err(LoadUserError::LoginFailed)
}
}
}
// You have access to the user via the AuthToken extractor in secured routes.
#[get("/secured")]
async fn secured(auth_token: AuthToken<User>) -> impl Responder {
let user = auth_token.authenticated_user();
HttpResponse::Ok().json(&*user)
}
#[actix_web::main]
async fn main() -> std::io::Result<()> {
let key = Key::generate();
HttpServer::new(move || {
// SessionLoginAppBuilder is the simplest way to create an App instance configured with session based authentication
// This default config registers handlers for: /login, /logout and /login/mfa.
SessionLoginAppBuilder::create(AuthenticationService, key.clone())
.build()
.service(secured)
})
.bind("127.0.0.1:7080")?
.run()
.await
}
#[get("/public")]
async fn public() -> impl Responder {
HttpResponse::Ok().json(r#"{ value: "everyone can see this" }"#)
}
#[actix_web::main]
async fn main() -> std::io::Result<()> {
let key = Key::generate();
HttpServer::new(move || {
SessionLoginAppBuilder::create(AuthenticationService, key.clone())
.set_login_routes_and_public_paths(Routes::default(), vec!["/public"])
.build()
.service(secured)
.service(public)
})
.bind("127.0.0.1:7080")?
.run()
.await
}