diff --git a/Cargo.lock b/Cargo.lock index 92e242e..fa25bcc 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -107,22 +107,6 @@ dependencies = [ "syn 2.0.48", ] -[[package]] -name = "async-tungstenite" -version = "0.17.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a1b71b31561643aa8e7df3effe284fa83ab1a840e52294c5f4bd7bfd8b2becbb" -dependencies = [ - "futures-io", - "futures-util", - "log", - "pin-project-lite", - "tokio", - "tokio-rustls 0.23.4", - "tungstenite 0.17.3", - "webpki-roots 0.22.6", -] - [[package]] name = "atoi" version = "2.0.0" @@ -174,12 +158,6 @@ dependencies = [ "rustc-demangle", ] -[[package]] -name = "base64" -version = "0.13.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8" - [[package]] name = "base64" version = "0.21.7" @@ -356,17 +334,6 @@ dependencies = [ "tokio", ] -[[package]] -name = "command_attr" -version = "0.4.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07b787d19b9806dd4c9c34b2b4147d1a61d6120d93ee289521ab9b0294d198e4" -dependencies = [ - "proc-macro2", - "quote", - "syn 1.0.109", -] - [[package]] name = "command_attr" version = "0.5.1" @@ -1004,10 +971,10 @@ dependencies = [ "futures-util", "http", "hyper", - "rustls 0.21.10", + "rustls", "rustls-native-certs", "tokio", - "tokio-rustls 0.24.1", + "tokio-rustls", ] [[package]] @@ -1442,15 +1409,6 @@ dependencies = [ "vcpkg", ] -[[package]] -name = "ordered-float" -version = "2.10.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "68f19d67e5a2795c94e73e0bb1cc1a7edeb2e28efd39e2e1c9b7a40c1108b11c" -dependencies = [ - "num-traits", -] - [[package]] name = "osuparse" version = "2.0.1" @@ -1700,7 +1658,7 @@ version = "0.11.24" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c6920094eb85afde5e4a138be3f2de8bbdf28000f0029e72c45025a56b042251" dependencies = [ - "base64 0.21.7", + "base64", "bytes", "encoding_rs", "futures-core", @@ -1720,7 +1678,7 @@ dependencies = [ "once_cell", "percent-encoding", "pin-project-lite", - "rustls 0.21.10", + "rustls", "rustls-pemfile", "serde", "serde_json", @@ -1729,7 +1687,7 @@ dependencies = [ "system-configuration", "tokio", "tokio-native-tls", - "tokio-rustls 0.24.1", + "tokio-rustls", "tokio-util", "tower-service", "url", @@ -1737,25 +1695,10 @@ dependencies = [ "wasm-bindgen-futures", "wasm-streams", "web-sys", - "webpki-roots 0.25.4", + "webpki-roots", "winreg", ] -[[package]] -name = "ring" -version = "0.16.20" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3053cf52e236a3ed746dfc745aa9cacf1b791d846bdaf412f60a8d7d6e17c8fc" -dependencies = [ - "cc", - "libc", - "once_cell", - "spin 0.5.2", - "untrusted 0.7.1", - "web-sys", - "winapi", -] - [[package]] name = "ring" version = "0.17.7" @@ -1766,7 +1709,7 @@ dependencies = [ "getrandom", "libc", "spin 0.9.8", - "untrusted 0.9.0", + "untrusted", "windows-sys 0.48.0", ] @@ -1851,18 +1794,6 @@ dependencies = [ "windows-sys 0.52.0", ] -[[package]] -name = "rustls" -version = "0.20.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1b80e3dec595989ea8510028f30c408a4630db12c9cbb8de34203b89d6577e99" -dependencies = [ - "log", - "ring 0.16.20", - "sct", - "webpki", -] - [[package]] name = "rustls" version = "0.21.10" @@ -1870,7 +1801,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f9d5a6813c0759e4609cd494e8e725babae6a2ca7b62a5536a13daaec6fcb7ba" dependencies = [ "log", - "ring 0.17.7", + "ring", "rustls-webpki", "sct", ] @@ -1893,7 +1824,7 @@ version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1c74cae0a4cf6ccbbf5f359f08efdf8ee7e1dc532573bf0db71968cb56b1448c" dependencies = [ - "base64 0.21.7", + "base64", ] [[package]] @@ -1902,16 +1833,10 @@ version = "0.101.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8b6275d1ee7a1cd780b64aca7726599a1dbc893b1e64144529e55c3c2f745765" dependencies = [ - "ring 0.17.7", - "untrusted 0.9.0", + "ring", + "untrusted", ] -[[package]] -name = "rustversion" -version = "1.0.14" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7ffc183a10b4478d04cbbbfc96d0873219d962dd5accaff2ffbd4ceb7df837f4" - [[package]] name = "ryu" version = "1.0.16" @@ -1948,8 +1873,8 @@ version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "da046153aa2352493d6cb7da4b6e5c0c057d8a1d0a9aa8560baffdd945acd414" dependencies = [ - "ring 0.17.7", - "untrusted 0.9.0", + "ring", + "untrusted", ] [[package]] @@ -2003,16 +1928,6 @@ dependencies = [ "serde_derive", ] -[[package]] -name = "serde-value" -version = "0.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f3a1a3341211875ef120e117ea7fd5228530ae7e7036a779fdc9117be6b3282c" -dependencies = [ - "ordered-float", - "serde", -] - [[package]] name = "serde_derive" version = "1.0.196" @@ -2059,42 +1974,6 @@ dependencies = [ "yaml-rust", ] -[[package]] -name = "serenity" -version = "0.11.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a7a89cef23483fc9d4caf2df41e6d3928e18aada84c56abd237439d929622c6" -dependencies = [ - "async-trait", - "async-tungstenite", - "base64 0.21.7", - "bitflags 1.3.2", - "bytes", - "cfg-if", - "chrono", - "command_attr 0.4.2", - "dashmap", - "flate2", - "futures", - "levenshtein", - "mime", - "mime_guess", - "parking_lot", - "percent-encoding", - "reqwest", - "rustversion", - "serde", - "serde-value", - "serde_json", - "static_assertions", - "time", - "tokio", - "tracing", - "typemap_rev 0.1.5", - "url", - "uwl", -] - [[package]] name = "serenity" version = "0.12.0" @@ -2103,11 +1982,11 @@ checksum = "385647faa24a889929028973650a4f158fb1b4272b2fcf94feb9fcc3c009e813" dependencies = [ "arrayvec", "async-trait", - "base64 0.21.7", + "base64", "bitflags 2.4.2", "bytes", "chrono", - "command_attr 0.5.1", + "command_attr", "dashmap", "flate2", "futures", @@ -2125,23 +2004,12 @@ dependencies = [ "tokio", "tokio-tungstenite", "tracing", - "typemap_rev 0.3.0", + "typemap_rev", "typesize", "url", "uwl", ] -[[package]] -name = "sha-1" -version = "0.10.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f5058ada175748e33390e40e872bd0fe59a19f265d0158daa551c5a88a76009c" -dependencies = [ - "cfg-if", - "cpufeatures", - "digest", -] - [[package]] name = "sha1" version = "0.10.6" @@ -2361,7 +2229,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e37195395df71fd068f6e2082247891bc11e3289624bbc776a0cdfa1ca7f1ea4" dependencies = [ "atoi", - "base64 0.21.7", + "base64", "bitflags 2.4.2", "byteorder", "bytes", @@ -2404,7 +2272,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d6ac0ac3b7ccd10cc96c7ab29791a7dd236bd94021f31eec7ba3d46a74aa1c24" dependencies = [ "atoi", - "base64 0.21.7", + "base64", "bitflags 2.4.2", "byteorder", "chrono", @@ -2664,24 +2532,13 @@ dependencies = [ "tokio", ] -[[package]] -name = "tokio-rustls" -version = "0.23.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c43ee83903113e03984cb9e5cebe6c04a5116269e900e3ddba8f068a62adda59" -dependencies = [ - "rustls 0.20.9", - "tokio", - "webpki", -] - [[package]] name = "tokio-rustls" version = "0.24.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081" dependencies = [ - "rustls 0.21.10", + "rustls", "tokio", ] @@ -2704,11 +2561,11 @@ checksum = "212d5dcb2a1ce06d81107c3d0ffa3121fe974b73f068c8282cb1c32328113b6c" dependencies = [ "futures-util", "log", - "rustls 0.21.10", + "rustls", "tokio", - "tokio-rustls 0.24.1", - "tungstenite 0.20.1", - "webpki-roots 0.25.4", + "tokio-rustls", + "tungstenite", + "webpki-roots", ] [[package]] @@ -2775,27 +2632,6 @@ version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e421abadd41a4225275504ea4d6566923418b7f05506fbc9c0fe86ba7396114b" -[[package]] -name = "tungstenite" -version = "0.17.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e27992fd6a8c29ee7eef28fc78349aa244134e10ad447ce3b9f0ac0ed0fa4ce0" -dependencies = [ - "base64 0.13.1", - "byteorder", - "bytes", - "http", - "httparse", - "log", - "rand", - "rustls 0.20.9", - "sha-1", - "thiserror", - "url", - "utf-8", - "webpki", -] - [[package]] name = "tungstenite" version = "0.20.1" @@ -2809,19 +2645,13 @@ dependencies = [ "httparse", "log", "rand", - "rustls 0.21.10", + "rustls", "sha1", "thiserror", "url", "utf-8", ] -[[package]] -name = "typemap_rev" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed5b74f0a24b5454580a79abb6994393b09adf0ab8070f15827cb666255de155" - [[package]] name = "typemap_rev" version = "0.3.0" @@ -2905,12 +2735,6 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "39ec24b3121d976906ece63c9daad25b85969647682eee313cb5779fdd69e14e" -[[package]] -name = "untrusted" -version = "0.7.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a156c684c91ea7d62626509bce3cb4e1d9ed5c4d978f7b4352658f96a4c26b4a" - [[package]] name = "untrusted" version = "0.9.0" @@ -3073,25 +2897,6 @@ dependencies = [ "wasm-bindgen", ] -[[package]] -name = "webpki" -version = "0.22.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed63aea5ce73d0ff405984102c42de94fc55a6b75765d621c65262469b3c9b53" -dependencies = [ - "ring 0.17.7", - "untrusted 0.9.0", -] - -[[package]] -name = "webpki-roots" -version = "0.22.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6c71e40d7d2c34a5106301fb632274ca37242cd0c9d3e64dbece371a40a2d87" -dependencies = [ - "webpki", -] - [[package]] name = "webpki-roots" version = "0.25.4" @@ -3301,7 +3106,7 @@ version = "0.1.0" dependencies = [ "dotenv", "env_logger", - "serenity 0.12.0", + "serenity", "tokio", "youmubot-cf", "youmubot-core", @@ -3323,7 +3128,7 @@ dependencies = [ "regex", "reqwest", "serde", - "serenity 0.12.0", + "serenity", "tokio", "youmubot-db", "youmubot-prelude", @@ -3339,7 +3144,7 @@ dependencies = [ "futures-util", "rand", "serde", - "serenity 0.11.7", + "serenity", "static_assertions", "tokio", "youmubot-db", @@ -3354,7 +3159,7 @@ dependencies = [ "dotenv", "rustbreak", "serde", - "serenity 0.12.0", + "serenity", ] [[package]] @@ -3385,7 +3190,7 @@ dependencies = [ "rosu-v2", "serde", "serde_json", - "serenity 0.12.0", + "serenity", "time", "youmubot-db", "youmubot-db-sql", @@ -3404,7 +3209,7 @@ dependencies = [ "flume 0.10.14", "futures-util", "reqwest", - "serenity 0.12.0", + "serenity", "tokio", "youmubot-db", "youmubot-db-sql", diff --git a/youmubot-core/Cargo.toml b/youmubot-core/Cargo.toml index 5552135..e1cda78 100644 --- a/youmubot-core/Cargo.toml +++ b/youmubot-core/Cargo.toml @@ -7,7 +7,7 @@ edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html [dependencies] -serenity = { version = "0.11.2", features = ["collector"] } +serenity = { version = "0.12", features = ["collector"] } rand = "0.8.5" serde = { version = "1.0.137", features = ["derive"] } chrono = "0.4.19" diff --git a/youmubot-core/src/admin/mod.rs b/youmubot-core/src/admin/mod.rs index 7c93c18..8df2c39 100644 --- a/youmubot-core/src/admin/mod.rs +++ b/youmubot-core/src/admin/mod.rs @@ -1,5 +1,6 @@ use futures_util::{stream, TryStreamExt}; use serenity::{ + builder::GetMessages, framework::standard::{ macros::{command, group}, Args, CommandResult, @@ -31,7 +32,7 @@ async fn clean(ctx: &Context, msg: &Message, mut args: Args) -> CommandResult { let limit = args.single().unwrap_or(10); let messages = msg .channel_id - .messages(&ctx.http, |b| b.before(msg.id).limit(limit)) + .messages(&ctx.http, GetMessages::new().before(msg.id).limit(limit)) .await?; let channel = msg.channel_id.to_channel(&ctx).await?; match &channel { diff --git a/youmubot-core/src/admin/soft_ban.rs b/youmubot-core/src/admin/soft_ban.rs index cba6bf1..cb41974 100644 --- a/youmubot-core/src/admin/soft_ban.rs +++ b/youmubot-core/src/admin/soft_ban.rs @@ -7,9 +7,7 @@ use serenity::{ channel::Message, id::{GuildId, RoleId, UserId}, }, - CacheAndHttp, }; -use std::sync::Arc; use youmubot_prelude::*; #[command] @@ -45,7 +43,7 @@ pub async fn soft_ban(ctx: &Context, msg: &Message, mut args: Args) -> CommandRe Some(v) => v, }; - let mut member = guild.member(&ctx, &user).await?; + let member = guild.member(&ctx, &user).await?; match duration { None if member.roles.contains(&role) => { msg.reply(&ctx, format!("⛓ Lifting soft-ban for user {}.", user.tag())) @@ -85,7 +83,7 @@ pub async fn soft_ban(ctx: &Context, msg: &Message, mut args: Args) -> CommandRe pub async fn soft_ban_init(ctx: &Context, msg: &Message, mut args: Args) -> CommandResult { let role_id = args.single::()?; let data = ctx.data.read().await; - let guild = msg.guild(ctx).unwrap(); + let guild = msg.guild_id.unwrap().to_partial_guild(&ctx).await?; // Check whether the role_id is the one we wanted if !guild.roles.contains_key(&role_id) { return Err(Error::msg(format!("{} is not a role in this server.", role_id)).into()); @@ -105,7 +103,7 @@ pub async fn soft_ban_init(ctx: &Context, msg: &Message, mut args: Args) -> Comm } // Watch the soft bans. Blocks forever. -pub async fn watch_soft_bans(cache_http: Arc, data: AppData) { +pub async fn watch_soft_bans(cache_http: impl CacheHttp, data: AppData) { loop { // Scope so that locks are released { @@ -115,7 +113,7 @@ pub async fn watch_soft_bans(cache_http: Arc, data: AppData) { let mut db = data.borrow().unwrap().clone(); let now = Utc::now(); for (server_id, bans) in db.iter_mut() { - let server_name: String = match server_id.to_partial_guild(&*cache_http.http).await + let server_name: String = match server_id.to_partial_guild(cache_http.http()).await { Err(_) => continue, Ok(v) => v.name, @@ -153,17 +151,17 @@ pub async fn watch_soft_bans(cache_http: Arc, data: AppData) { } async fn lift_soft_ban_for( - cache_http: &CacheAndHttp, + cache_http: impl CacheHttp, server_id: GuildId, server_name: &str, ban_role: RoleId, user_id: UserId, ) -> Result<()> { - let mut m = server_id.member(cache_http, user_id).await?; + let m = server_id.member(&cache_http, user_id).await?; println!( "Soft-ban for `{}` in server `{}` unlifted.", m.user.name, server_name ); - m.remove_role(&cache_http.http, ban_role).await?; + m.remove_role(cache_http.http(), ban_role).await?; Ok(()) } diff --git a/youmubot-core/src/community/mod.rs b/youmubot-core/src/community/mod.rs index 02ceb5c..700448f 100644 --- a/youmubot-core/src/community/mod.rs +++ b/youmubot-core/src/community/mod.rs @@ -3,6 +3,7 @@ use rand::{ thread_rng, }; use serenity::{ + builder::CreateMessage, framework::standard::{ macros::{command, group}, Args, CommandError as Error, CommandResult, @@ -62,13 +63,11 @@ pub async fn choose(ctx: &Context, m: &Message, mut args: Args) -> CommandResult let online_only = !flags.contains("everyone"); let users: Result, Error> = { - let guild = m.guild(ctx).unwrap(); - let presences = &guild.presences; + let presences = m.guild(&ctx.cache).unwrap().presences.clone(); let channel = m.channel_id.to_channel(&ctx).await?; if let Channel::Guild(channel) = channel { Ok(channel - .members(&ctx) - .await? + .members(&ctx)? .into_iter() .filter(|v| !v.user.bot) // Filter out bots .filter(|v| { @@ -84,9 +83,7 @@ pub async fn choose(ctx: &Context, m: &Message, mut args: Args) -> CommandResult }) .unwrap_or(false) }) - .map(future::ready) - .collect::>() - .filter_map(|member| async move { + .filter_map(|member| { // Filter by role if provided match role { Some(role) if member.roles.iter().any(|r| role == *r) => Some(member), @@ -94,8 +91,7 @@ pub async fn choose(ctx: &Context, m: &Message, mut args: Args) -> CommandResult _ => None, } }) - .collect() - .await) + .collect()) } else { unreachable!() } @@ -118,25 +114,27 @@ pub async fn choose(ctx: &Context, m: &Message, mut args: Args) -> CommandResult }; m.channel_id - .send_message(&ctx, |c| { - c.content( - MessageBuilder::new() - .push("👑 The Gensokyo gods have gathered around and decided, out of ") - .push_bold(format!("{}", users.len())) - .push(" ") - .push( - role.map(|r| format!("{}s", r.mention())) - .unwrap_or_else(|| "potential prayers".to_owned()), - ) - .push(", ") - .push(winner.mention()) - .push(" will be ") - .push_bold_safe(title) - .push(". Congrats! 🎉 🎊 🥳") - .build(), - ) - .reference_message(m) - }) + .send_message( + &ctx, + CreateMessage::new() + .content( + MessageBuilder::new() + .push("👑 The Gensokyo gods have gathered around and decided, out of ") + .push_bold(format!("{}", users.len())) + .push(" ") + .push( + role.map(|r| format!("{}s", r.mention())) + .unwrap_or_else(|| "potential prayers".to_owned()), + ) + .push(", ") + .push(winner.mention().to_string()) + .push(" will be ") + .push_bold_safe(title) + .push(". Congrats! 🎉 🎊 🥳") + .build(), + ) + .reference_message(m), + ) .await?; Ok(()) diff --git a/youmubot-core/src/community/roles.rs b/youmubot-core/src/community/roles.rs index 9c40489..8d340e6 100644 --- a/youmubot-core/src/community/roles.rs +++ b/youmubot-core/src/community/roles.rs @@ -1,5 +1,6 @@ use crate::db::Roles as DB; use serenity::{ + builder::EditMessage, framework::standard::{macros::command, Args, CommandResult}, model::{ channel::{Message, ReactionType}, @@ -100,7 +101,8 @@ async fn list(ctx: &Context, m: &Message, _: Args) -> CommandResult { m.push_line("```"); m.push(format!("Page **{}/{}**", page + 1, pages)); - msg.edit(ctx, |f| f.content(m.to_string())).await?; + msg.edit(ctx, EditMessage::new().content(m.to_string())) + .await?; Ok(true) }) }, @@ -140,7 +142,7 @@ async fn toggle(ctx: &Context, m: &Message, mut args: Args) -> CommandResult { m.reply(&ctx, "This role is not self-assignable. Check the `listroles` command to see which role can be assigned.").await?; } Some(role) => { - let mut member = guild.member(&ctx, m.author.id).await.unwrap(); + let member = guild.member(&ctx, m.author.id).await.unwrap(); if member.roles.contains(&role.id) { member.remove_role(&ctx, &role).await?; m.reply(&ctx, format!("Role `{}` has been removed.", role.name)) @@ -252,7 +254,7 @@ async fn remove(ctx: &Context, m: &Message, mut args: Args) -> CommandResult { /// Parse a string as a role. fn role_from_string(role: &str, roles: &std::collections::HashMap) -> Option { match role.parse::() { - Ok(id) if roles.contains_key(&RoleId(id)) => roles.get(&RoleId(id)).cloned(), + Ok(id) if roles.contains_key(&RoleId::new(id)) => roles.get(&RoleId::new(id)).cloned(), _ => roles .iter() .find_map(|(_, r)| if r.name == role { Some(r) } else { None }) @@ -417,7 +419,8 @@ mod reaction_watcher { use dashmap::DashMap; use flume::{Receiver, Sender}; use serenity::{ - collector::ReactionAction, + all::Reaction, + builder::{CreateMessage, EditMessage}, model::{ channel::{Message, ReactionType}, guild::Role as DiscordRole, @@ -468,7 +471,10 @@ mod reaction_watcher { roles: Vec<(Role, DiscordRole, ReactionType)>, ) -> Result<()> { let mut msg = channel - .send_message(&ctx, |c| c.content("Youmu is setting up the message...")) + .send_message( + &ctx, + CreateMessage::new().content("Youmu is setting up the message..."), + ) .await?; self.setup(&mut msg, ctx, guild, title, roles).await } @@ -481,8 +487,9 @@ mod reaction_watcher { roles: Vec<(Role, DiscordRole, ReactionType)>, ) -> Result<()> { // Send a message - msg.edit(&ctx, |m| { - m.content({ + msg.edit( + &ctx, + EditMessage::new().content({ let mut builder = serenity::utils::MessageBuilder::new(); builder .push_bold("Role Menu:") @@ -492,16 +499,16 @@ mod reaction_watcher { .push_line(""); for (role, discord_role, emoji) in &roles { builder - .push(emoji) + .push(emoji.to_string()) .push(" ") .push_bold_safe(&discord_role.name) .push(": ") .push_line_safe(&role.description) .push_line(""); } - builder - }) - }) + builder.build() + }), + ) .await?; // Do reactions for (_, _, emoji) in &roles { @@ -566,13 +573,19 @@ mod reaction_watcher { async fn handle(ctx: Context, recv: Receiver<()>, guild: GuildId, message: MessageId) { let mut recv = recv.into_recv_async(); - let collect = || { - serenity::collector::CollectReaction::new(&ctx) - .message_id(message) - .removed(true) - }; + let mut collect = serenity::collector::collect(&ctx.shard, move |event| { + match event { + serenity::all::Event::ReactionAdd(r) => Some((r.reaction.clone(), true)), + serenity::all::Event::ReactionRemove(r) => Some((r.reaction.clone(), false)), + _ => None, + } + .filter(|(r, _)| r.message_id == message) + }); + // serenity::collector::CollectReaction::new(&ctx) + // .message_id(message) + // .removed(true) loop { - let reaction = match future::select(recv, collect()).await { + let (reaction, is_add) = match future::select(recv, collect.next()).await { future::Either::Left(_) => break, future::Either::Right((r, new_recv)) => { recv = new_recv; @@ -582,8 +595,9 @@ mod reaction_watcher { } } }; - eprintln!("{:?}", reaction); - if let Err(e) = Self::handle_reaction(&ctx, guild, message, &reaction).await { + eprintln!("{:?} {}", reaction, is_add); + if let Err(e) = Self::handle_reaction(&ctx, guild, message, &reaction, is_add).await + { eprintln!("Handling {:?}: {}", reaction, e); break; } @@ -594,15 +608,16 @@ mod reaction_watcher { ctx: &Context, guild: GuildId, message: MessageId, - reaction: &ReactionAction, + reaction: &Reaction, + is_add: bool, ) -> Result<()> { let data = ctx.data.read().await; // Collect user - let user_id = match reaction.as_inner_ref().user_id { + let user_id = match reaction.user_id { Some(id) => id, None => return Ok(()), }; - let mut member = match guild.member(ctx, user_id).await.ok() { + let member = match guild.member(ctx, user_id).await.ok() { Some(m) => m, None => return Ok(()), }; @@ -620,7 +635,7 @@ mod reaction_watcher { .ok_or_else(|| Error::msg("message is no longer a role list handler"))? .iter() .find_map(|(role, role_reaction)| { - if &reaction.as_inner_ref().emoji == role_reaction { + if &reaction.emoji == role_reaction { Some(role.id) } else { None @@ -631,9 +646,10 @@ mod reaction_watcher { None => return Ok(()), }; - match reaction { - ReactionAction::Added(_) => member.add_role(&ctx, role).await.pls_ok(), - ReactionAction::Removed(_) => member.remove_role(&ctx, role).await.pls_ok(), + if is_add { + member.add_role(&ctx, role).await.pls_ok(); + } else { + member.remove_role(&ctx, role).await.pls_ok(); }; Ok(()) } diff --git a/youmubot-core/src/community/votes.rs b/youmubot-core/src/community/votes.rs index 7508031..ec9992e 100644 --- a/youmubot-core/src/community/votes.rs +++ b/youmubot-core/src/community/votes.rs @@ -1,18 +1,10 @@ -use serenity::framework::standard::CommandError as Error; -use serenity::{ - collector::ReactionAction, - framework::standard::{macros::command, Args, CommandResult}, - model::{ - channel::{Message, ReactionType}, - id::UserId, - }, - utils::MessageBuilder, -}; +use serenity::all::{Message, ReactionType, UserId}; +use serenity::builder::{CreateEmbed, CreateEmbedAuthor, CreateMessage}; +use serenity::framework::standard::macros::command; +use serenity::framework::standard::{Args, CommandError as Error, CommandResult}; +use serenity::{self, collector, utils::MessageBuilder}; +use std::collections::{HashMap as Map, HashSet as Set}; use std::time::Duration; -use std::{ - collections::{HashMap as Map, HashSet as Set}, - convert::TryFrom, -}; use youmubot_prelude::{Duration as ParseDuration, *}; #[command] @@ -86,18 +78,18 @@ pub async fn vote(ctx: &Context, msg: &Message, mut args: Args) -> CommandResult let author = msg.author.clone(); let asked = msg.timestamp; let until = *asked + (chrono::Duration::from_std(*duration).unwrap()); - let panel = channel.send_message(&ctx, |c| { - c.content("@here").embed(|e| { - e.author(|au| { - au.icon_url(author.avatar_url().unwrap_or_else(|| "".to_owned())) - .name(&author.name) + let panel = channel.send_message(&ctx, + CreateMessage::new().content("@here").embed( + CreateEmbed::new().author( { + CreateEmbedAuthor::new(&author.name).icon_url(author.avatar_url().unwrap_or_else(|| "".to_owned())) }) .title(format!("Please vote! Poll ends {}", until.format(""))) .thumbnail("https://images-ext-2.discordapp.net/external/BK7injOyt4XT8yNfbCDV4mAkwoRy49YPfq-3IwCc_9M/http/cdn.i.ntere.st/p/9197498/image") - .description(MessageBuilder::new().push_bold_line_safe(&question).push("\nThis question was asked by ").push(author.mention())) + .description( + MessageBuilder::new().push_bold_line_safe(&question).push("\nThis question was asked by ").push(author.mention().to_string()).build()) .fields(fields.into_iter()) - }) - }).await?; + ) + ).await?; msg.delete(&ctx).await?; // React on all the choices @@ -115,37 +107,38 @@ pub async fn vote(ctx: &Context, msg: &Message, mut args: Args) -> CommandResult .collect(); // Collect reactions... - let user_reactions = panel - .await_reactions(ctx) - .removed(true) - .timeout(*duration) - .build() - .fold(user_reactions, |mut set, reaction| async move { - let (reaction, is_add) = match &*reaction { - ReactionAction::Added(r) => (r, true), - ReactionAction::Removed(r) => (r, false), - }; - let users = if let ReactionType::Unicode(ref s) = reaction.emoji { - if let Some(users) = set.get_mut(s.as_str()) { - users - } else { - return set; - } + let message_id = panel.id; + let user_reactions = collector::collect(&ctx.shard, move |event| { + match event { + serenity::all::Event::ReactionAdd(r) => Some((r.reaction.clone(), true)), + serenity::all::Event::ReactionRemove(r) => Some((r.reaction.clone(), false)), + _ => None, + } + .filter(|(r, _)| r.message_id == message_id) + }) + .take_until(tokio::time::timeout(*duration, future::ready(()))) + .fold(user_reactions, |mut set, (reaction, is_add)| async move { + let users = if let ReactionType::Unicode(ref s) = reaction.emoji { + if let Some(users) = set.get_mut(s.as_str()) { + users } else { return set; - }; - let user_id = match reaction.user_id { - Some(v) => v, - None => return set, - }; - if is_add { - users.insert(user_id); - } else { - users.remove(&user_id); } - set - }) - .await; + } else { + return set; + }; + let user_id = match reaction.user_id { + Some(v) => v, + None => return set, + }; + if is_add { + users.insert(user_id); + } else { + users.remove(&user_id); + } + set + }) + .await; // Handle choices let choice_map = choices.into_iter().collect::>(); @@ -171,13 +164,14 @@ pub async fn vote(ctx: &Context, msg: &Message, mut args: Args) -> CommandResult } channel - .send_message(&ctx, |c| { - c.content({ + .send_message( + &ctx, + CreateMessage::new().content({ let mut content = MessageBuilder::new(); content .push("@here, ") - .push(asked.format(", ")) - .push(author.mention()) + .push(asked.format(", ").to_string()) + .push(author.mention().to_string()) .push(" asked ") .push_bold_safe(&question) .push(", and here are the results!"); @@ -199,8 +193,8 @@ pub async fn vote(ctx: &Context, msg: &Message, mut args: Args) -> CommandResult ); }); content.build() - }) - }) + }), + ) .await?; panel.delete(&ctx).await?; diff --git a/youmubot-core/src/fun/images.rs b/youmubot-core/src/fun/images.rs index 90abaa1..51ff4e7 100644 --- a/youmubot-core/src/fun/images.rs +++ b/youmubot-core/src/fun/images.rs @@ -1,4 +1,5 @@ use serde::Deserialize; +use serenity::builder::EditMessage; use serenity::framework::standard::CommandError as Error; use serenity::{ framework::standard::{ @@ -72,14 +73,15 @@ async fn message_command( if page >= images.len() { Ok(false) } else { - msg.edit(ctx, |f| { - f.content(format!( + msg.edit( + ctx, + EditMessage::new().content(format!( "[🖼️ **{}/{}**] Here's the image you requested!\n\n{}", page + 1, images.len(), images[page] - )) - }) + )), + ) .await .map(|_| true) .map_err(|e| e.into()) @@ -110,7 +112,6 @@ async fn get_image( )) .query(&[("limit", "50"), ("random", "true")]) .build()?; - println!("{:?}", req.url()); let response: Vec = client.execute(req).await?.json().await?; Ok(response .into_iter() diff --git a/youmubot-core/src/fun/names.rs b/youmubot-core/src/fun/names.rs index 9736e10..fd30491 100644 --- a/youmubot-core/src/fun/names.rs +++ b/youmubot-core/src/fun/names.rs @@ -3,7 +3,7 @@ use serenity::model::id::UserId; const ALL_NAMES: usize = FIRST_NAMES.len() * LAST_NAMES.len(); // Get a name from the user's id. pub fn name_from_userid(u: UserId) -> (&'static str, &'static str) { - let u = u.0 as usize % ALL_NAMES; + let u = u.get() as usize % ALL_NAMES; ( FIRST_NAMES[u / LAST_NAMES.len()], // Not your standard mod LAST_NAMES[u % LAST_NAMES.len()], diff --git a/youmubot-core/src/lib.rs b/youmubot-core/src/lib.rs index fc10c69..afeb39d 100644 --- a/youmubot-core/src/lib.rs +++ b/youmubot-core/src/lib.rs @@ -5,7 +5,7 @@ use serenity::{ model::{channel::Message, id::UserId}, }; use std::collections::HashSet; -use youmubot_prelude::*; +use youmubot_prelude::{announcer::CacheAndHttp, *}; pub mod admin; pub mod community; @@ -31,7 +31,7 @@ pub fn setup( // Create handler threads tokio::spawn(admin::watch_soft_bans( - client.cache_and_http.clone(), + CacheAndHttp::from_client(client), client.data.clone(), ));