use std::{collections::HashMap, sync::Arc}; use axum::{ extract::Query, http::StatusCode, routing::{get, post}, Extension, Json, }; use sqlx::SqlitePool; use crate::responses::registration::RegistrationResponse; use crate::{ models::devices::Device, responses::{flow::Flows, registration::RegistrationSuccess}, }; use crate::{ models::users::User, requests::registration::RegistrationRequest, responses::username_available::UsernameAvailable, types::{ authentication_data::AuthenticationData, identifier::Identifier, matrix_user_id::UserId, }, Config, }; pub fn routes() -> axum::Router { axum::Router::new() .route("/r0/login", get(get_login).post(post_login)) .route("/r0/register", post(post_register)) .route("/r0/register/available", get(get_username_available)) } #[tracing::instrument] async fn get_login() -> Json { Json(Flows::new()) } #[tracing::instrument(skip_all)] async fn post_login(body: String) -> StatusCode { dbg!(body); StatusCode::INTERNAL_SERVER_ERROR } #[tracing::instrument(skip_all)] async fn get_username_available( Extension(config): Extension>, Extension(db): Extension, Query(params): Query>, ) -> Json { let username = params.get("username").unwrap(); let user_id = UserId::new(&username, &config.homeserver_name).unwrap(); let exists = User::exists(&db, &user_id).await.unwrap(); Json(UsernameAvailable::new(!exists)) } #[tracing::instrument(skip_all)] async fn post_register( Extension(config): Extension>, Extension(db): Extension, Json(body): Json, Query(params): Query>, ) -> (StatusCode, Json) { // Client tries to get available flows if *&body.auth().is_none() { return ( StatusCode::UNAUTHORIZED, Json(RegistrationResponse::user_interactive_authorization_info()), ); } let (user, device) = match &body.auth().unwrap() { AuthenticationData::Password(auth_data) => { // let username = match auth_data.identifier() { // Identifier::User(user_identifier) => user_identifier.user().unwrap(), // }; let username = body.username().unwrap(); let user_id = UserId::new(&username, &config.homeserver_name).unwrap(); if User::exists(&db, &user_id).await.unwrap() { todo!("Error out") } let password = auth_data.password(); let display_name = match *&body.initial_device_display_name() { Some(display_name) => display_name.as_ref(), None => "Random displayname", }; let user = User::create(&db, &user_id, &user_id.to_string(), &password) .await .unwrap(); let device = Device::create(&db, &user, "test", display_name) .await .unwrap(); (user, device) } }; // dont log in the user after registration if *&body.inhibit_login().is_some() && *&body.inhibit_login().unwrap() { let resp = RegistrationSuccess::new(None, device.device_id(), user.user_id()); (StatusCode::OK, Json(RegistrationResponse::Success(resp))) } else { let session = device.create_session(&db).await.unwrap(); let resp = RegistrationSuccess::new(Some(session.value()), device.device_id(), user.user_id()); (StatusCode::OK, Json(RegistrationResponse::Success(resp))) } }