diff --git a/src/lib.rs b/src/lib.rs index 5be9207..64788b7 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -5,6 +5,7 @@ use sqlx::{Error, Pool, Sqlite}; use std::env; use std::str::FromStr; use std::time::{SystemTime, UNIX_EPOCH}; +use ldap3::{LdapConn, Scope, SearchEntry}; use tide::prelude::*; #[derive(Debug, Deserialize, Serialize, sqlx::FromRow)] @@ -19,7 +20,16 @@ pub struct AccountsPending { expiry: i64 } -pub async fn db_init(database: &str) -> Result, Error> { +#[derive(Debug, Deserialize, Serialize, sqlx::FromRow)] +pub struct Accounts { + user: String, + uid_number: i64, + discord: Option, + enabled: bool +} + +pub async fn db_init(config: &Config) -> Result, Error> { + let database = &config.database; let pool = SqlitePoolOptions::new() .max_connections(5) .connect_with(SqliteConnectOptions::from_str(&format!("sqlite://{}", database))?.create_if_missing(true)) @@ -39,12 +49,20 @@ pub async fn db_init(database: &str) -> Result, Error> { .execute(&pool) .await?; - // set up indexes? - /* - sqlx::query("CREATE INDEX IF NOT EXISTS index_estimate ON bus_results (valid_estimate)") - .execute(&pool) - .await?; - */ + // this is for active use + sqlx::query( + "CREATE TABLE IF NOT EXISTS accounts ( + user text primary key, + uid_number integer not null, + discord text, + enabled integer not null + )", + ).execute(&pool).await?; + + sqlx::query("CREATE INDEX IF NOT EXISTS index_uid_number ON accounts (uid_number)").execute(&pool).await?; + + update_accounts(&pool, config).await; + Ok(pool) } @@ -101,3 +119,61 @@ pub fn get_config() -> Config { config } + + +async fn update_accounts(pool: &Pool, config: &Config) { + let mut ldap = LdapConn::new(&config.ldap_host).unwrap(); + + ldap.simple_bind(&config.ldap_admin, &config.ldap_admin_pw).unwrap().success().unwrap(); + + if let Ok(x) = ldap.search("ou=users,dc=skynet,dc=ie", Scope::OneLevel, "(objectClass=*)", vec!["uid", "uidNumber", "skDiscord", "skMemberOf"]) { + + if let Ok((rs, _res)) = x.success() { + + for entry in rs { + let tmp = SearchEntry::construct(entry); + + let mut tmp_account = Accounts { + user: "".to_string(), + uid_number: 0, + discord: None, + enabled: false, + }; + + // pull out the required info + if tmp.attrs.contains_key("uid") && !tmp.attrs["uid"].is_empty() { + tmp_account.user = tmp.attrs["uid"][0].clone(); + } + if tmp.attrs.contains_key("uidNumber") && !tmp.attrs["uidNumber"].is_empty() { + tmp_account.uid_number = tmp.attrs["uidNumber"][0].clone().parse().unwrap_or(0); + } + if tmp.attrs.contains_key("skDiscord") && !tmp.attrs["skDiscord"].is_empty() { + tmp_account.user = tmp.attrs["skDiscord"][0].clone(); + } + if tmp.attrs.contains_key("skMemberOf") && !tmp.attrs["skMemberOf"].is_empty() && tmp.attrs["skMemberOf"].contains(&String::from("cn=skynet-users,ou=groups,dc=skynet,dc=ie")){ + tmp_account.enabled = true; + } + + if tmp_account.user.len() > 0 { + sqlx::query_as::<_, Accounts>( + " + INSERT OR REPLACE INTO accounts (user, uid_number, discord, enabled) + VALUES (?1, ?2, ?3, ?4) + ", + ) + .bind(&tmp_account.user) + .bind(&tmp_account.uid_number) + .bind(&tmp_account.discord) + .bind(&tmp_account.enabled) + .fetch_optional(pool) + .await + .ok(); + } + } + + } + } + + // done with ldap + ldap.unbind().unwrap(); +} diff --git a/src/main.rs b/src/main.rs index 0bb96b8..5ef4b16 100644 --- a/src/main.rs +++ b/src/main.rs @@ -5,7 +5,7 @@ use skynet_ldap_server::methods::account_new::{post_new_account, post_new_accoun #[async_std::main] async fn main() -> tide::Result<()> { let config = get_config(); - let db = db_init(&config.database).await?; + let db = db_init(&config).await?; let host_port = config.host_port.clone(); diff --git a/src/methods/account_new.rs b/src/methods/account_new.rs index 1b9f539..94473c3 100644 --- a/src/methods/account_new.rs +++ b/src/methods/account_new.rs @@ -255,7 +255,7 @@ pub async fn post_new_account_confirmation(mut req: Request) -> tide::Res DELETE FROM accounts_pending WHERE auth_code == ? "#, - ).bind(&auth_code).fetch_all(pool).await { + ).bind(&auth_code).fetch_all(db).await { println!("{:?}", results) }