pub mod account;
pub mod admin;
pub mod api;
pub mod audit;
pub mod billing;
pub mod bot;
pub mod changes;
pub mod crawls;
pub mod explorer;
pub mod export;
pub mod landing;
pub mod mcp;
pub mod monitoring;
pub mod quick;
pub mod rankorg;
pub mod search;
pub mod seo;
pub mod settings_alerts;
pub mod settings_keys;
pub mod sites;
use axum::Router;
use axum::extract::State;
use axum::response::{IntoResponse, Redirect, Response};
use axum::routing::get;
use crate::auth::CurrentUser;
use crate::config::Mode;
use crate::error::AppError;
use crate::state::AppState;
pub fn router() -> Router<AppState> {
Router::new()
.route("/", get(home))
.merge(account::routes())
.merge(sites::routes())
.merge(crawls::routes())
.merge(explorer::routes())
.merge(audit::routes())
.merge(changes::routes())
.merge(export::routes())
.merge(search::routes())
.merge(quick::routes())
.merge(monitoring::routes())
.merge(settings_alerts::routes())
.merge(settings_keys::routes())
.merge(api::routes())
.merge(billing::routes())
.merge(admin::routes())
.merge(rankorg::routes())
.route("/bot", get(bot::page))
.route("/robots.txt", get(seo::robots))
.route("/llms.txt", get(seo::llms))
.route("/sitemap.xml", get(seo::sitemap))
}
async fn home(
State(state): State<AppState>,
user: Option<CurrentUser>,
) -> Result<Response, AppError> {
let Some(user) = user else {
return if state.config.mode == Mode::Cloud {
landing::page(&state)
} else {
Ok(Redirect::to("/login?next=%2F").into_response())
};
};
let sites = codoseo_store::sites::list_for_account(&state.pool, user.id()).await?;
Ok(match sites.first() {
Some(s) => Redirect::to(&format!("/s/{}/audit", s.id)).into_response(),
None => Redirect::to("/sites").into_response(),
})
}