From 8b5a588770f907da70477a4d574d0a9fe53e3e91 Mon Sep 17 00:00:00 2001
From: Pavel Kirilin <win10@list.ru>
Date: Sun, 26 Feb 2023 20:49:03 +0400
Subject: [PATCH] Added @all handler for groups

Signed-off-by: Pavel Kirilin <win10@list.ru>
---
 src/bot/filters/message_fitlers.rs   | 12 ++++++++----
 src/bot/handlers/basic/mod.rs        |  1 +
 src/bot/handlers/basic/notify_all.rs | 28 ++++++++++++++++++++++++++++
 src/bot/main.rs                      | 23 ++++++++++++++---------
 4 files changed, 51 insertions(+), 13 deletions(-)
 create mode 100644 src/bot/handlers/basic/notify_all.rs

diff --git a/src/bot/filters/message_fitlers.rs b/src/bot/filters/message_fitlers.rs
index e947d4e..f60aac4 100644
--- a/src/bot/filters/message_fitlers.rs
+++ b/src/bot/filters/message_fitlers.rs
@@ -14,8 +14,9 @@ pub enum MessageDirection {
 
 #[derive(Clone, Copy, PartialEq, Eq, Debug)]
 pub enum TextMatchMethod {
-    IStartsWith,
-    IMatches,
+    StartsWith,
+    Matches,
+    Contains,
 }
 
 #[allow(dead_code)]
@@ -86,10 +87,13 @@ impl<'a> Filter for TextFilter<'a> {
         };
         for text in self.0 {
             let matches = match self.1 {
-                TextMatchMethod::IStartsWith => message_text
+                TextMatchMethod::StartsWith => message_text
                     .to_lowercase()
                     .starts_with(text.to_lowercase().as_str()),
-                TextMatchMethod::IMatches => message_text.to_lowercase() == text.to_lowercase(),
+                TextMatchMethod::Matches => message_text.to_lowercase() == text.to_lowercase(),
+                TextMatchMethod::Contains => message_text
+                    .to_lowercase()
+                    .contains(text.to_lowercase().as_str()),
             };
 
             if matches {
diff --git a/src/bot/handlers/basic/mod.rs b/src/bot/handlers/basic/mod.rs
index acc4306..c3bfd1a 100644
--- a/src/bot/handlers/basic/mod.rs
+++ b/src/bot/handlers/basic/mod.rs
@@ -1,4 +1,5 @@
 pub mod currency_converter;
 pub mod get_chat_id;
 pub mod help;
+pub mod notify_all;
 pub mod weather_forecaster;
diff --git a/src/bot/handlers/basic/notify_all.rs b/src/bot/handlers/basic/notify_all.rs
new file mode 100644
index 0000000..1155591
--- /dev/null
+++ b/src/bot/handlers/basic/notify_all.rs
@@ -0,0 +1,28 @@
+use grammers_client::{types::Chat, Client, Update};
+
+use crate::{bot::handlers::Handler, utils::messages::get_message};
+
+#[derive(Clone)]
+pub struct NotifyAll;
+
+#[async_trait::async_trait]
+impl Handler for NotifyAll {
+    async fn react(&self, client: &Client, update: &Update) -> anyhow::Result<()> {
+        let Some(message) = get_message(update) else {return Ok(());};
+        let Chat::Group(group) = message.chat() else {
+            return Ok(());
+        };
+        let mut participats_iter = client.iter_participants(group);
+        let mut response = String::new();
+        while let Some(participant) = participats_iter.next().await? {
+            if participant.user.is_bot() {
+                continue;
+            }
+            if let Some(username) = participant.user.username() {
+                response.push_str(format!("@{username} ").as_str());
+            }
+        }
+        message.reply(response).await?;
+        Ok(())
+    }
+}
diff --git a/src/bot/main.rs b/src/bot/main.rs
index 0182b64..f176268 100644
--- a/src/bot/main.rs
+++ b/src/bot/main.rs
@@ -20,6 +20,7 @@ use super::{
             currency_converter::{CurrencyConverter, CurrencyTextFilter},
             get_chat_id::GetChatId,
             help::Help,
+            notify_all::NotifyAll,
             weather_forecaster::WeatherForecaster,
         },
         fun::{
@@ -99,24 +100,23 @@ async fn run(args: BotConfig, client: Client) -> anyhow::Result<()> {
     let me = client.get_me().await?;
     let handlers: Vec<FilteredHandler> = vec![
         // Printing help.
-        FilteredHandler::new(Help).add_filter(TextFilter(&[".h"], TextMatchMethod::IMatches)),
+        FilteredHandler::new(Help).add_filter(TextFilter(&[".h"], TextMatchMethod::Matches)),
         // Greeting my fellow humans.
         FilteredHandler::new(Greeter)
             .add_filter(UpdateTypeFilter(&[UpdateType::New]))
             .add_filter(MessageDirectionFilter(MessageDirection::Incoming))
             .add_filter(SilentFilter)
             .add_filter(ExcludedChatsFilter(vec![me.id()]))
-            .add_filter(TextFilter(&["привет"], TextMatchMethod::IStartsWith))
+            .add_filter(TextFilter(&["привет"], TextMatchMethod::StartsWith))
             .add_filter(ExcludedChatsFilter(args.excluded_chats))
             .add_middleware::<MembersCount<100>>(),
         // Getting chat id.
-        FilteredHandler::new(GetChatId)
-            .add_filter(TextFilter(&[".cid"], TextMatchMethod::IMatches)),
+        FilteredHandler::new(GetChatId).add_filter(TextFilter(&[".cid"], TextMatchMethod::Matches)),
         // Make бля fun again.
         FilteredHandler::new(Blyaficator)
             .add_filter(UpdateTypeFilter(&[UpdateType::New]))
             .add_filter(SilentFilter)
-            .add_filter(TextFilter(&[".bl"], TextMatchMethod::IStartsWith)),
+            .add_filter(TextFilter(&[".bl"], TextMatchMethod::StartsWith)),
         // Handler for converting currecies.
         FilteredHandler::new(CurrencyConverter::new()?)
             .add_filter(UpdateTypeFilter(&[UpdateType::New]))
@@ -127,12 +127,12 @@ async fn run(args: BotConfig, client: Client) -> anyhow::Result<()> {
         FilteredHandler::new(Rotator)
             .add_filter(UpdateTypeFilter(&[UpdateType::New]))
             .add_filter(SilentFilter)
-            .add_filter(TextFilter(&[".rl"], TextMatchMethod::IStartsWith)),
+            .add_filter(TextFilter(&[".rl"], TextMatchMethod::StartsWith)),
         // Weather forecast.
         FilteredHandler::new(WeatherForecaster::new()?)
             .add_filter(UpdateTypeFilter(&[UpdateType::New]))
             .add_filter(SilentFilter)
-            .add_filter(TextFilter(&[".w"], TextMatchMethod::IStartsWith)),
+            .add_filter(TextFilter(&[".w"], TextMatchMethod::StartsWith)),
         // Smiley repeator.
         FilteredHandler::new(Repeator)
             .add_filter(UpdateTypeFilter(&[UpdateType::New]))
@@ -145,12 +145,17 @@ async fn run(args: BotConfig, client: Client) -> anyhow::Result<()> {
         FilteredHandler::new(MagicBall)
             .add_filter(UpdateTypeFilter(&[UpdateType::New]))
             .add_filter(SilentFilter)
-            .add_filter(TextFilter(&[".mb"], TextMatchMethod::IStartsWith)),
+            .add_filter(TextFilter(&[".mb"], TextMatchMethod::StartsWith)),
         // Random chooser.
         FilteredHandler::new(Chooser)
             .add_filter(UpdateTypeFilter(&[UpdateType::New]))
             .add_filter(SilentFilter)
-            .add_filter(TextFilter(&[".c"], TextMatchMethod::IStartsWith)),
+            .add_filter(TextFilter(&[".c"], TextMatchMethod::StartsWith)),
+        // Notify all.
+        FilteredHandler::new(NotifyAll)
+            .add_filter(UpdateTypeFilter(&[UpdateType::New]))
+            .add_filter(SilentFilter)
+            .add_filter(TextFilter(&["@all"], TextMatchMethod::Contains)),
     ];
 
     let mut errors_count = 0;
-- 
GitLab