From 5bfe47927d84add0a37caf9f6d9147d115418aa1 Mon Sep 17 00:00:00 2001 From: Mr-Andersen Date: Sat, 7 Sep 2019 14:58:47 +0300 Subject: [PATCH] Added Message --- src/core/types/chat.rs | 52 +++++------- src/core/types/message.rs | 174 ++++++++++++++++++++++++++++++++++++-- src/core/types/mod.rs | 4 +- 3 files changed, 191 insertions(+), 39 deletions(-) diff --git a/src/core/types/chat.rs b/src/core/types/chat.rs index 1382d6a8..d7226044 100644 --- a/src/core/types/chat.rs +++ b/src/core/types/chat.rs @@ -1,18 +1,18 @@ use crate::core::types::{ChatPermissions, ChatPhoto, Message}; -#[derive(Debug, Deserialize, Eq, Hash, PartialEq, Serialize)] +#[derive(Debug, Deserialize, Eq, Hash, PartialEq)] pub struct Chat { #[serde(rename = "chat_id")] - pub id: i32, + pub id: i64, #[serde(flatten)] - pub type_: ChatType, + pub chat_kind: ChatKind, #[serde(skip_serializing_if = "Option::is_none")] pub photo: Option, } -struct PrivateChatTypeVisitor; +struct PrivateChatKindVisitor; -impl<'de> serde::de::Visitor<'de> for PrivateChatTypeVisitor { +impl<'de> serde::de::Visitor<'de> for PrivateChatKindVisitor { type Value = (); fn expecting(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { @@ -36,51 +36,43 @@ impl<'de> serde::de::Visitor<'de> for PrivateChatTypeVisitor { fn assert_private_field<'de, D: serde::Deserializer<'de>>( des: D, ) -> Result<(), D::Error> { - des.deserialize_str(PrivateChatTypeVisitor) + des.deserialize_str(PrivateChatKindVisitor) } -fn serialize_private_field( +/*fn serialize_private_field( _: &(), ser: S, ) -> Result { ser.serialize_str("private") -} +}*/ -#[derive(Debug, Deserialize, Eq, Hash, PartialEq, Serialize)] -#[serde(rename_all = "snake_case")] +#[derive(Debug, Deserialize, Eq, Hash, PartialEq)] #[serde(untagged)] -pub enum ChatType { - NotPrivate { - #[serde(skip_serializing_if = "Option::is_none")] +pub enum ChatKind { + NonPrivate { title: Option, #[serde(flatten)] - type_: NotPrivateChatType, - #[serde(skip_serializing_if = "Option::is_none")] + non_private_chat_kind: NonPrivateChatKind, description: Option, - #[serde(skip_serializing_if = "Option::is_none")] invite_link: Option, - #[serde(skip_serializing_if = "Option::is_none")] pinned_message: Option>, }, Private { /// Dummy field. Used to ensure that "type" field is equal to "private" #[serde(rename = "type")] #[serde(deserialize_with = "assert_private_field")] - #[serde(serialize_with = "serialize_private_field")] + // #[serde(serialize_with = "serialize_private_field")] type_: (), - #[serde(skip_serializing_if = "Option::is_none")] username: Option, - #[serde(skip_serializing_if = "Option::is_none")] first_name: Option, - #[serde(skip_serializing_if = "Option::is_none")] last_name: Option, }, } -#[derive(Debug, Deserialize, Eq, Hash, PartialEq, Serialize)] +#[derive(Debug, Deserialize, Eq, Hash, PartialEq)] #[serde(rename_all = "snake_case")] #[serde(tag = "type")] -pub enum NotPrivateChatType { +pub enum NonPrivateChatKind { Channel { username: Option, }, @@ -98,16 +90,16 @@ pub enum NotPrivateChatType { #[cfg(test)] mod tests { use crate::core::types::*; - use serde_json::{from_str, to_string}; + use serde_json::from_str; #[test] fn channel_de() { assert_eq!( Chat { id: -1, - type_: ChatType::NotPrivate { + chat_kind: ChatKind::NonPrivate { title: None, - type_: NotPrivateChatType::Channel { + non_private_chat_kind: NonPrivateChatKind::Channel { username: Some("channelname".into()) }, description: None, @@ -128,7 +120,7 @@ mod tests { assert_eq!( Chat { id: 0, - type_: ChatType::Private { + chat_kind: ChatKind::Private { type_: (), username: Some("username".into()), first_name: Some("Anon".into()), @@ -146,12 +138,12 @@ mod tests { assert!(from_str::(r#"{"chat_id":0,"type":"WRONG"}"#).is_err()); } - #[test] + /*#[test] fn private_chat_ser() { assert_eq!( to_string(&Chat { id: 0, - type_: ChatType::Private { + type_: ChatKind::Private { type_: (), username: None, first_name: None, @@ -162,5 +154,5 @@ mod tests { .unwrap(), r#"{"chat_id":0,"type":"private"}"#.to_owned() ); - } + }*/ } diff --git a/src/core/types/message.rs b/src/core/types/message.rs index 636693e1..d58a7abd 100644 --- a/src/core/types/message.rs +++ b/src/core/types/message.rs @@ -4,17 +4,177 @@ use crate::core::types::{ SuccessfulPayment, User, Venue, Video, VideoNote, Voice, }; -#[derive(Debug, Deserialize, Eq, Hash, PartialEq, Serialize)] +#[derive(Debug, Deserialize, Eq, Hash, PartialEq)] pub struct Message { #[serde(rename = "message_id")] - pub id: i32, + pub id: i64, pub date: i32, - pub chat: Chat, + pub chat: Box, #[serde(flatten)] - pub type_: MessageType, + pub message_kind: MessageKind, } -#[derive(Debug, Deserialize, Eq, Hash, PartialEq, Serialize)] -#[serde(rename_all = "snake_case")] +#[derive(Debug, Deserialize, Eq, Hash, PartialEq)] #[serde(untagged)] -pub enum MessageType {} +pub enum MessageKind { + IncomingMessage { + #[serde(flatten)] + forward_kind: ForwardKind, + edit_date: Option, + #[serde(flatten)] + media_kind: MediaKind, + reply_markup: Option, + }, + NewChatMembers { + new_chat_members: Vec, + }, + LeftChatMember { + left_chat_member: User, + }, + NewChatTitle { + new_chat_title: String, + }, + NewChatPhoto { + new_chat_photo: Vec, + }, + DeleteChatPhoto { + delete_chat_photo: bool, + }, + GroupChatCreated { + group_chat_created: bool, + }, + SupergroupChatCreated { + supergroup_chat_created: bool, + }, + ChannelChatCreated { + channel_chat_created: bool, + }, + Migrate { + migrate_to_chat_id: i64, + migrate_from_chat_id: i64, + }, + PinnedMessage { + pinned_message: Box, + }, + Invoice { + invoice: Invoice, + }, + SuccessfulPayment { + successful_payment: SuccessfulPayment, + }, + ConnectedWebsite { + connected_website: String, + }, + PassportData { + passport_data: PassportData, + }, +} + +#[derive(Debug, Deserialize, Eq, Hash, PartialEq)] +#[serde(untagged)] +pub enum ForwardKind { + ChannelForward { + forward_from_channel: Box, + forward_from_message_id: i64, + forward_signature: String, + }, + NonChannelForward { + #[serde(flatten)] + forward: UserOrSenderName, + }, + Origin { + reply_to_message: Option>, + }, +} + +#[derive(Debug, Deserialize, Eq, Hash, PartialEq)] +#[serde(untagged)] +pub enum UserOrSenderName { + User { from: User }, + SenderName { sender_name: String }, +} + +#[derive(Debug, Deserialize, Eq, Hash, PartialEq)] +#[serde(untagged)] +pub enum MediaKind { + Animation { + animation: Animation, + caption: Option, + }, + Audio { + audio: Audio, + caption: Option, + }, + Contact { + contact: Contact, + }, + Document { + document: Document, + caption: Option, + }, + Game { + game: Game, + }, + Location { + location: Location, + }, + Photo { + sizes: Vec, + caption: Option, + }, + Poll { + poll: Poll, + }, + Sticker { + sticker: Sticker, + }, + Text { + text: String, + entities: Vec, + }, + Video { + video: Video, + caption: Option, + }, + VideoNote { + video_note: VideoNote, + }, + Voice { + voice: Voice, + caption: Option, + }, + Venue { + venue: Venue, + }, +} + +#[cfg(test)] +mod tests { + use crate::core::types::*; + use serde_json::from_str; + + #[test] + fn incoming_origin_de() { + assert_eq!(Message { + id: 0, + date: 0, + chat: Box::new(Chat { + id: 0, + chat_kind: ChatKind::Private { + type_: (), + username: None, + first_name: None, + last_name: None + }, + photo: None + }), + message_kind: MessageKind::IncomingMessage { + forward_kind: ForwardKind::Origin { reply_to_message: None }, + edit_date: None, + media_kind: MediaKind::Text { text: "Hello".to_string(), entities: vec![] }, + reply_markup: None + } + }, + from_str(r#"{"message_id":0,"date":0,"chat":{"chat_id":0,"type":"private"},"text":"Hello","entities":[]}"#).unwrap()); + } +} diff --git a/src/core/types/mod.rs b/src/core/types/mod.rs index 26531b6d..d1a801b2 100644 --- a/src/core/types/mod.rs +++ b/src/core/types/mod.rs @@ -4,7 +4,7 @@ pub use self::{ answer_pre_checkout_query::AnswerPreCheckoutQuery, answer_shipping_query::AnswerShippingQuery, audio::Audio, - chat::{Chat, ChatType, NotPrivateChatType}, + chat::{Chat, ChatKind, NonPrivateChatKind}, chat_member::ChatMember, chat_permissions::ChatPermissions, chat_photo::ChatPhoto, @@ -13,7 +13,7 @@ pub use self::{ input_media::InputMedia, invoice::Invoice, label_price::LabeledPrice, - message::Message, + message::{ForwardKind, MediaKind, Message, MessageKind, UserOrSenderName}, message_entity::MessageEntity, order_info::OrderInfo, parse_mode::ParseMode,