You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

95 lines
2.9 KiB
Rust

use axum::{
http::{header, Method},
middleware as axum_mw,
routing::{get, post, put},
Router,
};
use tower_http::cors::CorsLayer;
use tower_http::trace::TraceLayer;
use crate::app_state::AppState;
use crate::handlers;
use crate::middleware::auth;
pub fn create_router(state: AppState) -> Router {
let cors = CorsLayer::new()
.allow_origin(tower_http::cors::Any)
.allow_methods([Method::GET, Method::POST, Method::PUT, Method::DELETE])
.allow_headers([header::CONTENT_TYPE, header::AUTHORIZATION]);
// Public routes
let public = Router::new()
.route("/health", get(handlers::health::health_check))
.route("/api/v1/auth/register", post(handlers::auth::register))
.route("/api/v1/auth/login", post(handlers::auth::login))
.route(
"/api/v1/leaderboard",
get(handlers::leaderboard::get_leaderboard),
);
// Authenticated routes
let authenticated = Router::new()
.route("/api/v1/sessions", post(handlers::session::create_session))
.route(
"/api/v1/sessions/{id}",
get(handlers::session::get_session),
)
.route(
"/api/v1/sessions/{id}/end",
post(handlers::session::end_session),
)
.route(
"/api/v1/sessions/{id}/question",
get(handlers::game::get_current_question),
)
.route(
"/api/v1/sessions/{id}/question/{qid}/answer",
post(handlers::game::submit_answer),
)
.route(
"/api/v1/sessions/{id}/question/{qid}/hint",
post(handlers::game::request_hint),
)
.route(
"/api/v1/sessions/{id}/question/next",
post(handlers::game::next_question),
)
.layer(axum_mw::from_fn_with_state(
state.clone(),
auth::require_auth,
));
// Admin routes (auth + admin role)
let admin = Router::new()
.route(
"/api/v1/admin/questions",
get(handlers::admin::list_questions).post(handlers::admin::create_question),
)
.route(
"/api/v1/admin/questions/{id}",
put(handlers::admin::update_question)
.delete(handlers::admin::delete_question),
)
.route(
"/api/v1/admin/players",
get(handlers::admin::list_players),
)
.route(
"/api/v1/admin/players/{id}/role",
put(handlers::admin::update_player_role),
)
.layer(axum_mw::from_fn(auth::require_admin))
.layer(axum_mw::from_fn_with_state(
state.clone(),
auth::require_auth,
));
Router::new()
.merge(public)
.merge(authenticated)
.merge(admin)
.layer(TraceLayer::new_for_http())
.layer(cors)
.with_state(state)
}