This commit is contained in:
2025-10-09 22:16:29 +02:00
commit 768f8cb21c
33 changed files with 12047 additions and 0 deletions
+61
View File
@@ -0,0 +1,61 @@
use axum::{extract::State, http::StatusCode, response::IntoResponse, Json};
use diesel::prelude::*;
use serde::{Deserialize, Serialize};
use crate::{
auth::{password, AuthenticatedUser},
error::{AppError, AppResult},
models::User,
schema::users::dsl,
state::AppState,
};
#[derive(Deserialize)]
pub struct LoginRequest {
pub username: String,
pub password: String,
}
#[derive(Serialize)]
pub struct LoginResponse {
pub access_token: String,
pub token_type: String,
pub expires_in: i64,
}
pub async fn login(
State(state): State<AppState>,
Json(payload): Json<LoginRequest>,
) -> AppResult<Json<LoginResponse>> {
let mut conn = state.db()?;
let user: User = dsl::users
.filter(dsl::username.eq(&payload.username))
.first(&mut conn)?;
let valid = password::verify_password(&payload.password, &user.password_hash)
.map_err(|_| AppError::unauthorized())?;
if !valid {
return Err(AppError::unauthorized());
}
let token = state
.jwt
.generate_token(user.id, &user.username, &user.role)
.map_err(AppError::from)?;
Ok(Json(LoginResponse {
access_token: token,
token_type: "Bearer".to_string(),
expires_in: state.config.jwt_expiry_minutes * 60,
}))
}
pub async fn logout(_user: AuthenticatedUser) -> impl IntoResponse {
StatusCode::NO_CONTENT
}
pub async fn me(user: AuthenticatedUser) -> Json<AuthenticatedUser> {
Json(user)
}