use std::net::SocketAddr; use axum::{ extract::{FromRef, State}, response::IntoResponse, routing::get, Router, }; use nefarious_login::{ auth::AuthService, axum::{AuthController, UserFromSession}, introspection::IntrospectionService, login::{ config::{AuthEngine, ZitadelClap}, AuthClap, }, oauth::OAuth, session::{PostgresqlSessionClap, SessionBackend, SessionService}, }; use tracing_subscriber::EnvFilter; #[derive(Clone)] struct AppState { auth: AuthService, } #[tokio::main] async fn main() -> anyhow::Result<()> { tracing_subscriber::fmt() .with_env_filter(EnvFilter::from_default_env()) .init(); let auth = AuthClap { engine: AuthEngine::Zitadel, session_backend: SessionBackend::Postgresql, zitadel: ZitadelClap { authority_url: Some("https://personal-wxuujs.zitadel.cloud".into()), client_id: Some("237412977047895154@nefarious-test".into()), client_secret: Some( "rWwDi8gjNOyuMFKoOjNSlhjcVZ1B25wDh6HsDL27f0g2Hb0xGbvEf0WXFY2akOlL".into(), ), redirect_url: Some("http://localhost:3001/auth/authorized".into()), }, session: nefarious_login::session::SessionClap { postgresql: PostgresqlSessionClap { conn: Some("postgres://como:somenotverysecurepassword@localhost:5432/como".into()), }, }, }; let auth_service = AuthService::new_zitadel( OAuth::try_from(auth.clone())?, IntrospectionService::new_zitadel(&auth).await?, SessionService::new(&auth).await?, ); let state = AppState { auth: auth_service.clone(), }; let app = Router::new() .route("/unauthed", get(unauthed)) .route("/authed", get(authed)) .with_state(state) .nest("/auth", AuthController::new_router(auth_service).await?); let addr = SocketAddr::from(([127, 0, 0, 1], 3001)); println!("listening on: {addr}"); println!("open browser at: http://localhost:3001/auth/zitadel"); axum::Server::bind(&addr) .serve(app.into_make_service()) .await .unwrap(); Ok(()) } impl FromRef for AuthService { fn from_ref(input: &AppState) -> Self { input.auth.clone() } } async fn unauthed() -> String { "Hello Unauthorized User".into() } #[axum::debug_handler()] async fn authed( user: UserFromSession, State(_auth_service): State, ) -> impl IntoResponse { format!("Hello authorized user: {:?}", user.user.id) }