diff --git a/src/commands/add_minecraft.rs b/src/commands/add_minecraft.rs deleted file mode 100644 index 8b3ad0a..0000000 --- a/src/commands/add_minecraft.rs +++ /dev/null @@ -1,203 +0,0 @@ -use serenity::{ - builder::CreateApplicationCommand, - client::Context, - model::{ - application::interaction::application_command::ApplicationCommandInteraction, - prelude::{command::CommandOptionType, interaction::application_command::CommandDataOptionValue}, - }, -}; - -use skynet_discord_bot::{get_server_config, DataBase, Servers}; -use sqlx::{Pool, Sqlite}; - -pub(crate) mod user { - use super::*; - use crate::commands::link_email::link::get_server_member_discord; - use serenity::model::id::UserId; - use skynet_discord_bot::{whitelist_update, Config, Wolves, get_minecraft_config_server, Minecraft}; - use sqlx::Error; - - pub fn register(command: &mut CreateApplicationCommand) -> &mut CreateApplicationCommand { - command.name("link_minecraft").description("Link your minecraft account").create_option(|option| { - option - .name("minecraft-username") - .description("Your Minecraft username") - .kind(CommandOptionType::String) - .required(true) - }) - } - - pub async fn run(command: &ApplicationCommandInteraction, ctx: &Context) -> String { - let db_lock = { - let data_read = ctx.data.read().await; - data_read.get::().expect("Expected Databse in TypeMap.").clone() - }; - let db = db_lock.read().await; - - let config_lock = { - let data_read = ctx.data.read().await; - data_read.get::().expect("Expected Config in TypeMap.").clone() - }; - let config = config_lock.read().await; - - // user has to have previously linked with wolves - if get_server_member_discord(&db, &command.user.id).await.is_none() { - return "Not linked with wolves, please use ``/link_wolves`` with your wolves email.".to_string(); - } - - let username = if let CommandDataOptionValue::String(username) = command - .data - .options - .first() - .expect("Expected username option") - .resolved - .as_ref() - .expect("Expected username object") - { - username.trim() - } else { - return "Please provide a valid username".to_string(); - }; - - // insert the username into the database - match add_minecraft(&db, &command.user.id, username).await { - Ok(_) => {} - Err(e) => { - dbg!("{:?}", e); - return format!("Failure to minecraft username {:?}", username); - } - } - - // get a list of servers that the user is a member of - if let Ok(servers) = get_servers(&db, &command.user.id).await { - for server in servers { - whitelist_update(&vec![username.to_string()], &server.minecraft, &config.discord_minecraft).await; - } - } - - "Added/Updated minecraft_user info".to_string() - } - - async fn add_minecraft(db: &Pool, user: &UserId, minecraft: &str) -> Result, Error> { - sqlx::query_as::<_, Wolves>( - " - UPDATE wolves - SET minecraft = ?2 - WHERE discord = ?1; - ", - ) - .bind(*user.as_u64() as i64) - .bind(minecraft) - .fetch_optional(db) - .await - } - - async fn get_servers(db: &Pool, discord: &UserId) -> Result, Error> { - sqlx::query_as::<_, Minecraft>( - " - SELECT minecraft.* - FROM minecraft - JOIN ( - SELECT server - FROM server_members - JOIN wolves USING (id_wolves) - WHERE discord = ?1 - ) sub on minecraft.server_discord = sub.server - ", - ) - .bind(*discord.as_u64() as i64) - .fetch_all(db) - .await - } -} - -pub(crate) mod server { - use sqlx::Error; - // this is to managfe the server side of commands related to minecraft - use super::*; - use skynet_discord_bot::{is_admin, update_server, Config}; - - pub fn register(command: &mut CreateApplicationCommand) -> &mut CreateApplicationCommand { - command - .name("add_minecraft") - .description("Enable the bot for this discord") - .create_option(|option| { - option - .name("server_id") - .description("ID of the Minecraft server hosted by the Computer Society") - .kind(CommandOptionType::String) - .required(true) - }) - } - - pub async fn run(command: &ApplicationCommandInteraction, ctx: &Context) -> String { - // check if user has high enough permisssions - if let Some(msg) = is_admin(command, ctx).await { - return msg; - } - let g_id = match command.guild_id { - None => return "Not in a server".to_string(), - Some(x) => x, - }; - - let server_minecraft = if let CommandDataOptionValue::String(id) = command - .data - .options - .first() - .expect("Expected server_id option") - .resolved - .as_ref() - .expect("Expected server_id object") - { - id.to_owned() - } else { - return String::from("Expected Server ID"); - }; - - let db_lock = { - let data_read = ctx.data.read().await; - data_read.get::().expect("Expected Databse in TypeMap.").clone() - }; - let db = db_lock.read().await; - - let server_data = match get_server_config(&db, &g_id).await { - None => { - return "No existing server config, have you used ``/add``?".to_string(); - } - Some(x) => { - x - } - }; - - match add_server(&db, *server_data.server.as_u64() as i64, &server_minecraft).await { - Ok(_) => {} - Err(e) => { - println!("{:?}", e); - return format!("Failure to insert into Minecraft {} {}", *server_data.server.as_u64(), &server_minecraft); - } - } - - let config_lock = { - let data_read = ctx.data.read().await; - data_read.get::().expect("Expected Config in TypeMap.").clone() - }; - let config = config_lock.read().await; - - update_server(&server_minecraft, &db, &g_id, &config).await; - - "Added/Updated minecraft_server info".to_string() - } - - async fn add_server(db: &Pool, discord: i64, minecraft: &str ) -> Result, Error> { - sqlx::query_as::<_, Servers>( - " - INSERT OR REPLACE INTO minecraft (server_discord, server_minecraft) - VALUES (?1, ?2) - ", - ) - .bind(discord) - .bind(minecraft) - .fetch_optional(db) - .await - } -} diff --git a/src/commands/minecraft.rs b/src/commands/minecraft.rs new file mode 100644 index 0000000..c346009 --- /dev/null +++ b/src/commands/minecraft.rs @@ -0,0 +1,210 @@ +use serenity::{ + builder::CreateApplicationCommand, + client::Context, + model::{ + application::interaction::application_command::ApplicationCommandInteraction, + prelude::{command::CommandOptionType, interaction::application_command::CommandDataOptionValue}, + }, +}; + +use skynet_discord_bot::{get_server_config, DataBase, Servers}; +use sqlx::{Pool, Sqlite}; + +pub(crate) mod user { + use super::*; + pub(crate) mod add { + use super::*; + use crate::commands::link_email::link::get_server_member_discord; + use serenity::model::id::UserId; + use skynet_discord_bot::{whitelist_update, Config, Wolves, Minecraft}; + use sqlx::Error; + + pub fn register(command: &mut CreateApplicationCommand) -> &mut CreateApplicationCommand { + command.name("link_minecraft").description("Link your minecraft account").create_option(|option| { + option + .name("minecraft-username") + .description("Your Minecraft username") + .kind(CommandOptionType::String) + .required(true) + }) + } + + pub async fn run(command: &ApplicationCommandInteraction, ctx: &Context) -> String { + let db_lock = { + let data_read = ctx.data.read().await; + data_read.get::().expect("Expected Databse in TypeMap.").clone() + }; + let db = db_lock.read().await; + + let config_lock = { + let data_read = ctx.data.read().await; + data_read.get::().expect("Expected Config in TypeMap.").clone() + }; + let config = config_lock.read().await; + + // user has to have previously linked with wolves + if get_server_member_discord(&db, &command.user.id).await.is_none() { + return "Not linked with wolves, please use ``/link_wolves`` with your wolves email.".to_string(); + } + + let username = if let CommandDataOptionValue::String(username) = command + .data + .options + .first() + .expect("Expected username option") + .resolved + .as_ref() + .expect("Expected username object") + { + username.trim() + } else { + return "Please provide a valid username".to_string(); + }; + + // insert the username into the database + match add_minecraft(&db, &command.user.id, username).await { + Ok(_) => {} + Err(e) => { + dbg!("{:?}", e); + return format!("Failure to minecraft username {:?}", username); + } + } + + // get a list of servers that the user is a member of + if let Ok(servers) = get_servers(&db, &command.user.id).await { + for server in servers { + whitelist_update(&vec![username.to_string()], &server.minecraft, &config.discord_minecraft).await; + } + } + + "Added/Updated minecraft_user info".to_string() + } + + async fn add_minecraft(db: &Pool, user: &UserId, minecraft: &str) -> Result, Error> { + sqlx::query_as::<_, Wolves>( + " + UPDATE wolves + SET minecraft = ?2 + WHERE discord = ?1; + ", + ) + .bind(*user.as_u64() as i64) + .bind(minecraft) + .fetch_optional(db) + .await + } + + async fn get_servers(db: &Pool, discord: &UserId) -> Result, Error> { + sqlx::query_as::<_, Minecraft>( + " + SELECT minecraft.* + FROM minecraft + JOIN ( + SELECT server + FROM server_members + JOIN wolves USING (id_wolves) + WHERE discord = ?1 + ) sub on minecraft.server_discord = sub.server + ", + ) + .bind(*discord.as_u64() as i64) + .fetch_all(db) + .await + } + } +} + +pub(crate) mod server { + use super::*; + + pub(crate) mod add { + use sqlx::Error; + // this is to managfe the server side of commands related to minecraft + use super::*; + use skynet_discord_bot::{is_admin, update_server, Config}; + + pub fn register(command: &mut CreateApplicationCommand) -> &mut CreateApplicationCommand { + command + .name("add_minecraft") + .description("Enable the bot for this discord") + .create_option(|option| { + option + .name("server_id") + .description("ID of the Minecraft server hosted by the Computer Society") + .kind(CommandOptionType::String) + .required(true) + }) + } + + pub async fn run(command: &ApplicationCommandInteraction, ctx: &Context) -> String { + // check if user has high enough permisssions + if let Some(msg) = is_admin(command, ctx).await { + return msg; + } + let g_id = match command.guild_id { + None => return "Not in a server".to_string(), + Some(x) => x, + }; + + let server_minecraft = if let CommandDataOptionValue::String(id) = command + .data + .options + .first() + .expect("Expected server_id option") + .resolved + .as_ref() + .expect("Expected server_id object") + { + id.to_owned() + } else { + return String::from("Expected Server ID"); + }; + + let db_lock = { + let data_read = ctx.data.read().await; + data_read.get::().expect("Expected Databse in TypeMap.").clone() + }; + let db = db_lock.read().await; + + let server_data = match get_server_config(&db, &g_id).await { + None => { + return "No existing server config, have you used ``/add``?".to_string(); + } + Some(x) => { + x + } + }; + + match add_server(&db, *server_data.server.as_u64() as i64, &server_minecraft).await { + Ok(_) => {} + Err(e) => { + println!("{:?}", e); + return format!("Failure to insert into Minecraft {} {}", *server_data.server.as_u64(), &server_minecraft); + } + } + + let config_lock = { + let data_read = ctx.data.read().await; + data_read.get::().expect("Expected Config in TypeMap.").clone() + }; + let config = config_lock.read().await; + + update_server(&server_minecraft, &db, &g_id, &config).await; + + "Added/Updated minecraft_server info".to_string() + } + + async fn add_server(db: &Pool, discord: i64, minecraft: &str) -> Result, Error> { + sqlx::query_as::<_, Servers>( + " + INSERT OR REPLACE INTO minecraft (server_discord, server_minecraft) + VALUES (?1, ?2) + ", + ) + .bind(discord) + .bind(minecraft) + .fetch_optional(db) + .await + } + } +} diff --git a/src/commands/mod.rs b/src/commands/mod.rs index 95e0c51..0a1d475 100644 --- a/src/commands/mod.rs +++ b/src/commands/mod.rs @@ -1,3 +1,3 @@ -pub mod add_minecraft; +pub mod minecraft; pub mod add_server; pub mod link_email; diff --git a/src/main.rs b/src/main.rs index 67d54f2..619a750 100644 --- a/src/main.rs +++ b/src/main.rs @@ -60,8 +60,8 @@ impl EventHandler for Handler { .create_application_command(|command| commands::add_server::register(command)) .create_application_command(|command| commands::link_email::link::register(command)) .create_application_command(|command| commands::link_email::verify::register(command)) - .create_application_command(|command| commands::add_minecraft::server::register(command)) - .create_application_command(|command| commands::add_minecraft::user::register(command)) + .create_application_command(|command| commands::minecraft::server::add::register(command)) + .create_application_command(|command| commands::minecraft::user::add::register(command)) }) .await { @@ -81,10 +81,10 @@ impl EventHandler for Handler { // user commands "link_wolves" => commands::link_email::link::run(&command, &ctx).await, "verify" => commands::link_email::verify::run(&command, &ctx).await, - "link_minecraft" => commands::add_minecraft::user::run(&command, &ctx).await, + "link_minecraft" => commands::minecraft::user::add::run(&command, &ctx).await, // admin commands "add" => commands::add_server::run(&command, &ctx).await, - "add_minecraft" => commands::add_minecraft::server::run(&command, &ctx).await, + "add_minecraft" => commands::minecraft::server::add::run(&command, &ctx).await, _ => "not implemented :(".to_string(), };