diff --git a/Cargo.lock b/Cargo.lock index 276aca2..c932230 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -962,6 +962,8 @@ dependencies = [ "crates_io_api", "log", "pretty_env_logger", + "serde", + "serde_json", "teloxide", "tokio", "url", diff --git a/Cargo.toml b/Cargo.toml index 980c21c..3c17fb6 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -13,3 +13,5 @@ tokio = { version = "1.8", features = ["rt-multi-thread", "macros"] } url = "2.4.1" crates_io_api = "0.8.2" uuid = { version = "1.5.0", features = ["v4"] } +serde_json = "1.0.108" +serde = { version = "1.0.192", features = ["derive"] } diff --git a/src/functions/about.rs b/src/functions/about.rs index 880b3ba..b69f96d 100644 --- a/src/functions/about.rs +++ b/src/functions/about.rs @@ -1,4 +1,4 @@ -use crate::{hooks, utils::kbmng::Keyboard}; +use crate::{hooks, utils::keyboard_manager::Keyboard}; use teloxide::{ payloads::SendMessageSetters, prelude::*, diff --git a/src/functions/groups.rs b/src/functions/groups.rs index 54eff8a..1ecc0f9 100644 --- a/src/functions/groups.rs +++ b/src/functions/groups.rs @@ -1,4 +1,4 @@ -use crate::utils::kbmng::Keyboard; +use crate::utils::{group_manager::Groups, keyboard_manager::Keyboard}; use teloxide::{ payloads::SendMessageSetters, prelude::*, @@ -7,27 +7,31 @@ use teloxide::{ static TEXT: &str = "Telegramdagi Rust Hamjamiyatlari yoki Guruhlari:\nAgar o'zingizni guruhingizni qo'shmoqchi bo'lsangiz, bizni community.json ni yangilang!"; -pub fn keyboard() -> InlineKeyboardMarkup { - let mut keyboard = Keyboard::new(); - keyboard.url("Jamiyat", "https://t.me/rustlanguz"); - keyboard.url("Web Sahifa", "https://rust-lang.uz") -} - pub async fn command(bot: &Bot, msg: &Message) -> ResponseResult<()> { + let groups: Groups = Groups::new(); + bot.send_message(msg.chat.id, TEXT) .parse_mode(ParseMode::Html) - .reply_markup(keyboard()) + .reply_markup(keyboard(&groups, 1)) .await?; Ok(()) } pub async fn callback(bot: &Bot, q: &CallbackQuery, args: &Vec<&str>) -> ResponseResult<()> { + let groups: Groups = Groups::new(); + + // Parse page + let page: i32 = match args[1].parse() { + Ok(page) => page, + Err(_) => 1, + }; + if args.is_empty() { if let Some(Message { id, chat, .. }) = q.message.clone() { bot.edit_message_text(chat.id, id, TEXT) .parse_mode(ParseMode::Html) - .reply_markup(keyboard()) + .reply_markup(keyboard(&groups, page)) .await?; } else if let Some(id) = q.inline_message_id.clone() { bot.edit_message_text_inline(id, "Oopsie, something went wrong...") @@ -37,3 +41,29 @@ pub async fn callback(bot: &Bot, q: &CallbackQuery, args: &Vec<&str>) -> Respons Ok(()) } + +pub fn keyboard(groups: &Groups, page: i32) -> InlineKeyboardMarkup { + let mut keyboard = Keyboard::new(); + + for group in groups.get_groups(page, 5) { + keyboard.text( + &group.name, + &format!( + "detail_{}_{}", + page, + group.telegram.clone().replace("@", "") + ), + ); + keyboard.row(); + } + + if !groups.get_groups(page + 1, 5).is_empty() { + keyboard.text(&"Keyingi ➡️", &format!("group_{}", page + 1)); + } + + if page > 1 { + keyboard.text(&"⬅️ Oldingi", &format!("group_{}", page - 1)); + } + + keyboard.get() +} diff --git a/src/functions/inline.rs b/src/functions/inline.rs index ca4b39f..6601478 100644 --- a/src/functions/inline.rs +++ b/src/functions/inline.rs @@ -2,7 +2,7 @@ use crates_io_api::{AsyncClient, Crate, CratesQuery}; use std::error::Error; use teloxide::{prelude::*, types::*}; -use crate::utils::inmgr::*; +use crate::utils::inline_manager::*; pub async fn inline( bot: Bot, diff --git a/src/functions/mod.rs b/src/functions/mod.rs index 1c12ce3..1406d06 100644 --- a/src/functions/mod.rs +++ b/src/functions/mod.rs @@ -31,6 +31,8 @@ pub async fn commands( pub async fn callback(bot: Bot, q: CallbackQuery) -> Result<(), Box> { let mut args: Vec<&str> = Vec::new(); + println!("Receiving callback: {:?}", q.data); + if let Some(data) = q.data.clone() { if data.contains("_") { args = data.split("_").collect(); @@ -38,6 +40,8 @@ pub async fn callback(bot: Bot, q: CallbackQuery) -> Result<(), Box crate::functions::groups::callback(&bot, &q, &args).await, _ => Ok(()), diff --git a/src/functions/rules.rs b/src/functions/rules.rs index 79a3220..b80923b 100644 --- a/src/functions/rules.rs +++ b/src/functions/rules.rs @@ -1,4 +1,4 @@ -use crate::{hooks, utils::kbmng::Keyboard}; +use crate::{hooks, utils::keyboard_manager::Keyboard}; use teloxide::{ payloads::SendMessageSetters, prelude::*, diff --git a/src/functions/start.rs b/src/functions/start.rs index a80f014..d4c3974 100644 --- a/src/functions/start.rs +++ b/src/functions/start.rs @@ -1,4 +1,4 @@ -use crate::utils::kbmng::Keyboard; +use crate::utils::keyboard_manager::Keyboard; use teloxide::{ payloads::SendMessageSetters, prelude::*, diff --git a/src/hooks/is_private.rs b/src/hooks/is_private.rs index 5282ce5..96192be 100644 --- a/src/hooks/is_private.rs +++ b/src/hooks/is_private.rs @@ -4,7 +4,7 @@ use teloxide::{ types::{InlineKeyboardMarkup, ParseMode}, }; -use crate::utils::kbmng::Keyboard; +use crate::utils::keyboard_manager::Keyboard; static TEXT: &str = "⚠️ Bu komanda faqat shaxsiy chat uchun!"; diff --git a/src/utils/group_manager.rs b/src/utils/group_manager.rs new file mode 100644 index 0000000..77cea14 --- /dev/null +++ b/src/utils/group_manager.rs @@ -0,0 +1,45 @@ +use serde::{Deserialize, Serialize}; + +static GROUPS: &str = include_str!("../../communities.json"); + +#[derive(Serialize, Deserialize, Clone, Debug)] +pub struct Group { + pub name: String, + pub about: String, + pub telegram: String, + pub link: Option, +} + +#[derive(Debug, Clone)] +pub struct Groups { + groups: Vec, +} + +impl Groups { + pub fn new() -> Self { + let json: Vec = serde_json::from_str(GROUPS).unwrap(); + + Self { groups: json } + } + + pub fn get_groups(&self, page_number: i32, page_size: i32) -> Vec { + let start = (page_number - 1) * page_size; + let end = page_number * page_size; + + println!("start: {}, end: {}", start, end); + + if start < 0 || end < 0 { + return Vec::new(); + } + + if start as usize > self.groups.len() { + return Vec::new(); + } + + if end as usize > self.groups.len() { + return self.groups[start as usize..].to_vec(); + } + + self.groups[start as usize..end as usize].to_vec() + } +} diff --git a/src/utils/grpmgr.rs b/src/utils/grpmgr.rs deleted file mode 100644 index e69de29..0000000 diff --git a/src/utils/inmgr.rs b/src/utils/inline_manager.rs similarity index 98% rename from src/utils/inmgr.rs rename to src/utils/inline_manager.rs index bc9e447..8d7d76c 100644 --- a/src/utils/inmgr.rs +++ b/src/utils/inline_manager.rs @@ -1,4 +1,4 @@ -use super::kbmng::Keyboard; +use super::keyboard_manager::Keyboard; use crates_io_api::Crate; use teloxide::types::*; diff --git a/src/utils/kbmng.rs b/src/utils/keyboard_manager.rs similarity index 94% rename from src/utils/kbmng.rs rename to src/utils/keyboard_manager.rs index 90a8394..e1ebf4d 100644 --- a/src/utils/kbmng.rs +++ b/src/utils/keyboard_manager.rs @@ -20,7 +20,7 @@ impl Keyboard { } /// Add a text callback to keyboard - pub fn text(&mut self, text: &String, callback: &String) -> InlineKeyboardMarkup { + pub fn text(&mut self, text: &str, callback: &str) -> InlineKeyboardMarkup { self.keyboard .last_mut() .unwrap() diff --git a/src/utils/mod.rs b/src/utils/mod.rs index 3c91cd1..39d3ae4 100644 --- a/src/utils/mod.rs +++ b/src/utils/mod.rs @@ -1,2 +1,3 @@ -pub mod inmgr; -pub mod kbmng; +pub mod group_manager; +pub mod inline_manager; +pub mod keyboard_manager;