//! Assembles the HTTP application from shared infrastructure and domain modules.
use axum::extract::State;
use axum::http::StatusCode;
use axum::routing::get;
use axum::{Json, Router};
use serde::Serialize;
use crate::base::state::AppState;
use crate::modules;
pub fn router(state: AppState) -> Router {
Router::new()
.route("/health", get(health))
.merge(modules::routes())
.with_state(state)
}
#[derive(Serialize)]
struct Health {
status: &'static str,
app: String,
database: &'static str,
}
/// Reports whether the app is up and its database reachable (503 if not).
async fn health(State(state): State<AppState>) -> (StatusCode, Json<Health>) {
// `query`, not `execute`: Turso rejects `execute` for statements that return rows.
let database_ok = match state.database.connect().await {
Ok(conn) => conn.query("SELECT 1", ()).await.is_ok(),
Err(_) => false,
};
let (status, database) = if database_ok {
(StatusCode::OK, "ok")
} else {
(StatusCode::SERVICE_UNAVAILABLE, "unavailable")
};
let body = Health {
status: if database_ok { "ok" } else { "degraded" },
app: state.config.name.clone(),
database,
};
(status, Json(body))
}