fix some things

This commit is contained in:
nora 2022-06-15 21:45:36 +02:00
parent afd5e49eda
commit 835665e77f
3 changed files with 162 additions and 51 deletions

View file

@ -39,6 +39,13 @@ fn slash_commands(commands: &mut CreateApplicationCommands) -> &mut CreateApplic
.kind(ApplicationCommandOptionType::User) .kind(ApplicationCommandOptionType::User)
.required(true) .required(true)
}) })
.create_sub_option(|option| {
option
.name("judge")
.description("Der Richter")
.kind(ApplicationCommandOptionType::User)
.required(true)
})
.create_sub_option(|option| { .create_sub_option(|option| {
option option
.name("reason") .name("reason")
@ -182,17 +189,19 @@ async fn lawsuit_command_handler(
"create" => { "create" => {
let plaintiff = UserOption::get(options.get(0)).wrap_err("plaintiff")?; let plaintiff = UserOption::get(options.get(0)).wrap_err("plaintiff")?;
let accused = UserOption::get(options.get(1)).wrap_err("accused")?; let accused = UserOption::get(options.get(1)).wrap_err("accused")?;
let reason = StringOption::get(options.get(2)).wrap_err("reason")?; let judge = UserOption::get(options.get(2)).wrap_err("judge")?;
let reason = StringOption::get(options.get(3)).wrap_err("reason")?;
let plaintiff_layer = let plaintiff_layer =
UserOption::get_optional(options.get(3)).wrap_err("plaintiff_layer")?; UserOption::get_optional(options.get(4)).wrap_err("plaintiff_layer")?;
let accused_layer = let accused_layer =
UserOption::get_optional(options.get(4)).wrap_err("accused_layer")?; UserOption::get_optional(options.get(5)).wrap_err("accused_layer")?;
let mut lawsuit = Lawsuit { let mut lawsuit = Lawsuit {
plaintiff: plaintiff.0.id, plaintiff: plaintiff.0.id.to_string(),
accused: accused.0.id, accused: accused.0.id.to_string(),
plaintiff_layer: plaintiff_layer.map(|l| l.0.id), judge: judge.0.id.to_string(),
accused_layer: accused_layer.map(|l| l.0.id), plaintiff_layer: plaintiff_layer.map(|l| l.0.id.to_string()),
accused_layer: accused_layer.map(|l| l.0.id.to_string()),
reason: reason.to_owned(), reason: reason.to_owned(),
state: LawsuitState::Initial, state: LawsuitState::Initial,
court_room: None, court_room: None,

View file

@ -4,12 +4,7 @@ use color_eyre::Result;
use serde::{Deserialize, Serialize}; use serde::{Deserialize, Serialize};
use serenity::{ use serenity::{
http::Http, http::Http,
model::{ model::{channel::PermissionOverwriteType, id::ChannelId, prelude::*, Permissions},
channel::PermissionOverwriteType,
id::{ChannelId, UserId},
prelude::{GuildId, PermissionOverwrite},
Permissions,
},
}; };
use tracing::info; use tracing::info;
@ -24,13 +19,14 @@ pub enum LawsuitState {
#[derive(Debug, Clone, Serialize, Deserialize)] #[derive(Debug, Clone, Serialize, Deserialize)]
pub struct Lawsuit { pub struct Lawsuit {
pub plaintiff: UserId, pub plaintiff: String,
pub accused: UserId, pub accused: String,
pub plaintiff_layer: Option<UserId>, pub plaintiff_layer: Option<String>,
pub accused_layer: Option<UserId>, pub accused_layer: Option<String>,
pub judge: String,
pub reason: String, pub reason: String,
pub state: LawsuitState, pub state: LawsuitState,
pub court_room: Option<ChannelId>, pub court_room: Option<String>,
} }
impl Lawsuit { impl Lawsuit {
@ -44,14 +40,18 @@ impl Lawsuit {
.find_or_insert_state(&guild_id.to_string()) .find_or_insert_state(&guild_id.to_string())
.await?; .await?;
let free_room = state.court_rooms.iter().find(|r| !r.ongoing_lawsuit); let free_room = state
.court_rooms
.iter()
.find(|r| !r.ongoing_lawsuit)
.cloned();
match (free_room, &state.court_category) { let room = match (free_room, &state.court_category) {
(Some(_room), _) => Ok(Response::Simple("a free room? rip".to_owned())), (Some(room), _) => room,
(None, Some(category)) => { (None, Some(category)) => {
// create room // create room
create_room( let result = create_room(
http, http,
guild_id, guild_id,
state.court_rooms.len(), state.court_rooms.len(),
@ -61,13 +61,93 @@ impl Lawsuit {
.await .await
.wrap_err("create new room")?; .wrap_err("create new room")?;
Ok(Response::Simple("no free room? rip".to_owned())) match result {
Err(res) => return Ok(res),
Ok(room) => room,
} }
(None, None) => Ok(Response::Simple( }
(None, None) => return Ok(Response::Simple(
"Zuerst eine Kategorie für die Gerichtsräume festlegen mit `/lawsuit set_category`" "Zuerst eine Kategorie für die Gerichtsräume festlegen mit `/lawsuit set_category`"
.to_owned(), .to_owned(),
)), )),
};
self.court_room = Some(room.channel_id.clone());
let result = self
.send_process_open_message(http, guild_id, &room)
.await
.wrap_err("send process open message")?;
if let Err(response) = result {
return Ok(response);
} }
// TODO: now give the people their roles
Ok(Response::Simple(format!(
"ha eine ufgmacht im channel <#{}>",
room.channel_id
)))
}
async fn send_process_open_message(
&self,
http: &Http,
guild_id: GuildId,
room: &CourtRoom,
) -> Result<Result<(), Response>> {
let channels = guild_id
.to_partial_guild(http)
.await
.wrap_err("fetch partial guild")?
.channels(http)
.await
.wrap_err("fetch channels")?;
let channel = channels.get(&ChannelId::from_str(&room.channel_id).expect("oh god"));
match channel {
Some(channel) => {
channel
.id
.send_message(http, |msg| {
msg.embed(|embed| {
embed
.title("Prozess")
.field("Grund", &self.reason, false)
.field("Kläger", format!("<@{}>", self.plaintiff), false)
.field(
"Anwalt des Klägers",
match &self.plaintiff_layer {
Some(lawyer) => format!("<@{}>", lawyer),
None => "TBD".to_string(),
},
false,
)
.field("Angeklagter", format!("<@{}>", self.accused), false)
.field(
"Anwalt des Angeklagten",
match &self.accused_layer {
Some(lawyer) => format!("<@{}>", lawyer),
None => "TBD".to_string(),
},
false,
)
.field("Richter", format!("<@{}>", self.judge), false)
})
})
.await
.wrap_err("send message")?;
}
None => {
// todo: remove the court room from the db
return Ok(Err(Response::Simple(
"i ha de channel zum de prozess öffne nöd gfunde".to_string(),
)));
}
}
Ok(Ok(()))
} }
} }
@ -77,7 +157,7 @@ async fn create_room(
room_len: usize, room_len: usize,
category_id: ChannelId, category_id: ChannelId,
mongo_client: &Mongo, mongo_client: &Mongo,
) -> Result<()> { ) -> Result<Result<CourtRoom, Response>> {
let room_number = room_len + 1; let room_number = room_len + 1;
let room_name = format!("gerichtsraum-{room_number}"); let room_name = format!("gerichtsraum-{room_number}");
let role_name = format!("Gerichtsprozess {room_number}"); let role_name = format!("Gerichtsprozess {room_number}");
@ -87,14 +167,32 @@ async fn create_room(
.await .await
.wrap_err("fetch partial guild")?; .wrap_err("fetch partial guild")?;
let court_role = guild let role_id = match guild.role_by_name(&role_name) {
Some(role) => role.id,
None => {
guild
.create_role(http, |role| { .create_role(http, |role| {
role.name(role_name).permissions(Permissions::empty()) role.name(role_name).permissions(Permissions::empty())
}) })
.await .await
.wrap_err("create role")?; .wrap_err("create role")?
.id
}
};
let channel = guild let channels = guild.channels(http).await.wrap_err("fetching channels")?;
let channel_id = match channels.values().find(|c| c.name() == room_name) {
Some(channel) => {
if channel.parent_id != Some(category_id) {
return Ok(Err(Response::Simple(format!(
"de channel {room_name} isch i de falsche kategorie, man eh"
))));
}
channel.id
}
None => {
guild
.create_channel(http, |channel| { .create_channel(http, |channel| {
channel channel
.name(room_name) .name(room_name)
@ -102,24 +200,27 @@ async fn create_room(
.permissions(vec![PermissionOverwrite { .permissions(vec![PermissionOverwrite {
allow: Permissions::SEND_MESSAGES, allow: Permissions::SEND_MESSAGES,
deny: Permissions::empty(), deny: Permissions::empty(),
kind: PermissionOverwriteType::Role(court_role.id), kind: PermissionOverwriteType::Role(role_id),
}]) }])
}) })
.await .await
.wrap_err("create channel")?; .wrap_err("create channel")?
.id
}
};
let room = CourtRoom { let room = CourtRoom {
channel_id: channel.id.to_string(), channel_id: channel_id.to_string(),
ongoing_lawsuit: false, ongoing_lawsuit: false,
role_id: court_role.id.to_string(), role_id: role_id.to_string(),
}; };
mongo_client mongo_client
.add_court_room(&guild_id.to_string(), room) .add_court_room(&guild_id.to_string(), &room)
.await .await
.wrap_err("add court room to database")?; .wrap_err("add court room to database")?;
info!(guild_id = %guild_id, channel_id = %channel.id, "Created new court room"); info!(guild_id = %guild_id, channel_id = %channel_id, "Created new court room");
Ok(()) Ok(Ok(room))
} }

View file

@ -1,5 +1,6 @@
use color_eyre::Result; use color_eyre::Result;
use mongodb::{ use mongodb::{
bson,
bson::doc, bson::doc,
options::{ClientOptions, Credential}, options::{ClientOptions, Credential},
Client, Collection, Database, Client, Collection, Database,
@ -98,12 +99,12 @@ impl Mongo {
Ok(()) Ok(())
} }
pub async fn add_court_room(&self, guild_id: &str, room: CourtRoom) -> Result<()> { pub async fn add_court_room(&self, guild_id: &str, room: &CourtRoom) -> Result<()> {
let _ = self.find_or_insert_state(guild_id).await?; let _ = self.find_or_insert_state(guild_id).await?;
let coll = self.state_coll(); let coll = self.state_coll();
coll.update_one( coll.update_one(
doc! {"guild_id": &guild_id }, doc! {"guild_id": &guild_id },
doc! {"$push": { "court_rooms": &serde_json::to_string(&room).unwrap() }}, doc! {"$push": { "court_rooms": bson::to_bson(room).wrap_err("invalid bson for room")? }},
None, None,
) )
.await .await