1use std::future::IntoFuture;
2
3use url::Url;
4
5use crate::{
6 payloads::{
7 AnswerInlineQuery, AnswerWebAppQuery, CopyMessage, EditEphemeralMessageCaption,
8 EditEphemeralMessageMedia, EditEphemeralMessageText, EditMessageCaption,
9 EditMessageCaptionInline, EditMessageChecklist, EditMessageMedia, EditMessageMediaInline,
10 EditMessageText, EditMessageTextInline, EditStory, GiftPremiumSubscription, PostStory,
11 SavePreparedInlineMessage, SendAnimation, SendAudio, SendChecklist, SendDocument, SendGift,
12 SendGiftChat, SendLivePhoto, SendMediaGroup, SendMessage, SendMessageDraft, SendPaidMedia,
13 SendPhoto, SendPoll, SendVideo, SendVoice,
14 },
15 prelude::Requester,
16 requests::{HasPayload, Output, Request},
17 types::*,
18};
19
20#[derive(Clone, Debug)]
23pub struct DefaultParseMode<B> {
24 bot: B,
25 mode: ParseMode,
26}
27
28#[derive(Clone)]
30pub struct DefaultParseModeRequest<R> {
31 req: R,
32 mode: ParseMode,
33}
34
35impl<B> DefaultParseMode<B> {
36 pub fn new(bot: B, parse_mode: ParseMode) -> Self {
42 Self { bot, mode: parse_mode }
43 }
44
45 pub fn inner(&self) -> &B {
47 &self.bot
48 }
49
50 pub fn into_inner(self) -> B {
52 self.bot
53 }
54
55 pub fn parse_mode(&self) -> ParseMode {
57 self.mode
58 }
59}
60
61impl<R> Request for DefaultParseModeRequest<R>
62where
63 R: Request + Clone,
64 R::Payload: VisitParseModes,
65{
66 type Err = R::Err;
67 type Send = R::Send;
68 type SendRef = R::Send;
69
70 fn send(mut self) -> Self::Send {
72 self.req.payload_mut().visit_parse_modes(|mode| _ = mode.get_or_insert(self.mode));
73 self.req.send()
74 }
75
76 fn send_ref(&self) -> Self::SendRef {
77 self.clone().send()
79 }
80}
81
82impl<R> IntoFuture for DefaultParseModeRequest<R>
83where
84 Self: Request,
85{
86 type Output = Result<Output<Self>, <Self as Request>::Err>;
87 type IntoFuture = <Self as Request>::Send;
88
89 fn into_future(self) -> Self::IntoFuture {
90 self.send()
91 }
92}
93
94impl<R> HasPayload for DefaultParseModeRequest<R>
95where
96 R: Request,
97{
98 type Payload = R::Payload;
99
100 fn payload_mut(&mut self) -> &mut Self::Payload {
101 self.req.payload_mut()
102 }
103
104 fn payload_ref(&self) -> &Self::Payload {
105 self.req.payload_ref()
106 }
107}
108
109macro_rules! f {
110 ($m:ident $this:ident ($($arg:ident : $T:ty),*)) => {
111 {
112 let req = $this.inner().$m($($arg),*);
113 DefaultParseModeRequest { req, mode: $this.mode }
114 }
115 };
116}
117
118macro_rules! fty {
119 ($T:ident) => {
120 DefaultParseModeRequest<B::$T>
121 };
122}
123
124macro_rules! ftyid {
125 ($T:ident) => {
126 B::$T
127 };
128}
129
130macro_rules! fid {
131 ($m:ident $this:ident ($($arg:ident : $T:ty),*)) => {
132 $this.inner().$m($($arg),*)
133 };
134}
135
136impl<B> Requester for DefaultParseMode<B>
137where
138 B: Requester,
139 B::SendMessage: Clone,
140 B::SendMessageDraft: Clone,
141 B::SendPhoto: Clone,
142 B::SendVideo: Clone,
143 B::SendAudio: Clone,
144 B::SendDocument: Clone,
145 B::SendAnimation: Clone,
146 B::SendVoice: Clone,
147 B::SendLivePhoto: Clone,
148 B::EditMessageText: Clone,
149 B::EditMessageTextInline: Clone,
150 B::EditMessageCaption: Clone,
151 B::EditMessageCaptionInline: Clone,
152 B::SendPoll: Clone,
153 B::SendChecklist: Clone,
154 B::CopyMessage: Clone,
155 B::PostStory: Clone,
156 B::EditStory: Clone,
157 B::AnswerInlineQuery: Clone,
158 B::AnswerWebAppQuery: Clone,
159 B::SavePreparedInlineMessage: Clone,
160 B::EditMessageMedia: Clone,
161 B::EditMessageMediaInline: Clone,
162 B::EditMessageChecklist: Clone,
163 B::SendPaidMedia: Clone,
164 B::SendMediaGroup: Clone,
165 B::GiftPremiumSubscription: Clone,
166 B::SendGift: Clone,
167 B::SendGiftChat: Clone,
168 B::EditEphemeralMessageText: Clone,
169 B::EditEphemeralMessageMedia: Clone,
170 B::EditEphemeralMessageCaption: Clone,
171{
172 type Err = B::Err;
173
174 requester_forward! {
175 send_message,
176 send_message_draft,
177 send_photo,
178 send_video,
179 send_audio,
180 send_document,
181 send_animation,
182 send_voice,
183 send_poll,
184 send_checklist,
185 edit_message_text,
186 edit_message_text_inline,
187 edit_message_caption,
188 edit_message_caption_inline,
189 edit_message_checklist,
190 copy_message,
191 post_story,
192 edit_story,
193 answer_inline_query,
194 answer_web_app_query,
195 save_prepared_inline_message,
196 send_paid_media,
197 send_media_group,
198 edit_message_media,
199 edit_message_media_inline,
200 gift_premium_subscription,
201 send_gift,
202 send_gift_chat,
203 edit_ephemeral_message_text,
204 edit_ephemeral_message_media,
205 edit_ephemeral_message_caption,
206 => f, fty
207 }
208
209 requester_forward! {
210 get_me,
211 log_out,
212 close,
213 get_updates,
214 set_webhook,
215 delete_webhook,
216 get_webhook_info,
217 forward_message,
218 forward_messages,
219 copy_messages,
220 send_rich_message,
221 send_rich_message_draft,
222 send_video_note,
223 send_location,
224 edit_message_live_location,
225 edit_message_live_location_inline,
226 stop_message_live_location,
227 stop_message_live_location_inline,
228 send_venue,
229 send_contact,
230 send_dice,
231 send_chat_action,
232 set_message_reaction,
233 get_user_profile_photos,
234 get_user_profile_audios,
235 set_user_emoji_status,
236 get_file,
237 kick_chat_member,
238 ban_chat_member,
239 unban_chat_member,
240 restrict_chat_member,
241 promote_chat_member,
242 set_chat_administrator_custom_title,
243 set_chat_member_tag,
244 ban_chat_sender_chat,
245 unban_chat_sender_chat,
246 set_chat_permissions,
247 export_chat_invite_link,
248 create_chat_invite_link,
249 edit_chat_invite_link,
250 create_chat_subscription_invite_link,
251 edit_chat_subscription_invite_link,
252 revoke_chat_invite_link,
253 set_chat_photo,
254 delete_chat_photo,
255 set_chat_title,
256 set_chat_description,
257 pin_chat_message,
258 unpin_chat_message,
259 unpin_all_chat_messages,
260 leave_chat,
261 get_chat,
262 get_chat_administrators,
263 get_chat_members_count,
264 get_chat_member_count,
265 get_chat_member,
266 set_chat_sticker_set,
267 delete_chat_sticker_set,
268 get_forum_topic_icon_stickers,
269 create_forum_topic,
270 edit_forum_topic,
271 close_forum_topic,
272 reopen_forum_topic,
273 delete_forum_topic,
274 unpin_all_forum_topic_messages,
275 edit_general_forum_topic,
276 close_general_forum_topic,
277 reopen_general_forum_topic,
278 hide_general_forum_topic,
279 unhide_general_forum_topic,
280 unpin_all_general_forum_topic_messages,
281 answer_callback_query,
282 get_user_chat_boosts,
283 set_my_commands,
284 get_business_connection,
285 get_my_commands,
286 set_my_name,
287 get_my_name,
288 set_my_description,
289 get_my_description,
290 set_my_short_description,
291 get_my_short_description,
292 set_my_profile_photo,
293 remove_my_profile_photo,
294 get_managed_bot_token,
295 replace_managed_bot_token,
296 save_prepared_keyboard_button,
297 send_live_photo,
298 get_user_personal_chat_messages,
299 answer_guest_query,
300 get_managed_bot_access_settings,
301 set_managed_bot_access_settings,
302 delete_message_reaction,
303 delete_all_message_reactions,
304 set_chat_menu_button,
305 get_chat_menu_button,
306 set_my_default_administrator_rights,
307 get_my_default_administrator_rights,
308 delete_my_commands,
309 edit_message_reply_markup,
310 edit_message_reply_markup_inline,
311 stop_poll,
312 approve_suggested_post,
313 decline_suggested_post,
314 delete_message,
315 delete_messages,
316 send_sticker,
317 get_sticker_set,
318 get_custom_emoji_stickers,
319 upload_sticker_file,
320 create_new_sticker_set,
321 add_sticker_to_set,
322 set_sticker_position_in_set,
323 delete_sticker_from_set,
324 replace_sticker_in_set,
325 set_sticker_set_thumbnail,
326 set_custom_emoji_sticker_set_thumbnail,
327 set_sticker_set_title,
328 delete_sticker_set,
329 set_sticker_emoji_list,
330 set_sticker_keywords,
331 set_sticker_mask_position,
332 get_available_gifts,
333 verify_user,
334 verify_chat,
335 remove_user_verification,
336 remove_chat_verification,
337 read_business_message,
338 delete_business_messages,
339 set_business_account_name,
340 set_business_account_username,
341 set_business_account_bio,
342 set_business_account_profile_photo,
343 remove_business_account_profile_photo,
344 set_business_account_gift_settings,
345 get_business_account_star_balance,
346 transfer_business_account_stars,
347 get_business_account_gifts,
348 get_user_gifts,
349 get_chat_gifts,
350 repost_story,
351 convert_gift_to_stars,
352 upgrade_gift,
353 transfer_gift,
354 delete_story,
355 send_invoice,
356 create_invoice_link,
357 answer_shipping_query,
358 answer_pre_checkout_query,
359 get_my_star_balance,
360 get_star_transactions,
361 refund_star_payment,
362 edit_user_star_subscription,
363 set_passport_data_errors,
364 send_game,
365 set_game_score,
366 set_game_score_inline,
367 get_game_high_scores,
368 approve_chat_join_request,
369 decline_chat_join_request,
370 answer_chat_join_request_query,
371 send_chat_join_request_web_app,
372 edit_ephemeral_message_reply_markup,
373 delete_ephemeral_message
374 => fid, ftyid
375 }
376}
377
378download_forward! {
379 B
380 DefaultParseMode<B>
381 { this => this.inner() }
382}
383
384trait VisitParseModes {
385 fn visit_parse_modes(&mut self, visitor: impl FnMut(&mut Option<ParseMode>));
386}
387
388macro_rules! impl_visit_parse_modes {
389 (
390 $(
391 $T:ty => [
392 $(
393 $field:ident
394 ),*
395 ]
396 ,
397 )*
398 ) => {
399 $(
400 impl VisitParseModes for $T {
401 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
402 $(
403 visitor(&mut self.$field);
404 )*
405 }
406 }
407 )*
408 }
409}
410
411impl_visit_parse_modes! {
412 SendMessage => [parse_mode],
413 SendMessageDraft => [parse_mode],
414 SendPhoto => [parse_mode],
415 SendVideo => [parse_mode],
416 SendAudio => [parse_mode],
417 SendDocument => [parse_mode],
418 SendAnimation => [parse_mode],
419 SendVoice => [parse_mode],
420 SendLivePhoto => [parse_mode],
421 EditMessageText => [parse_mode],
422 EditMessageTextInline => [parse_mode],
423 EditMessageCaption => [parse_mode],
424 EditMessageCaptionInline => [parse_mode],
425 SendPaidMedia => [parse_mode],
426 GiftPremiumSubscription => [text_parse_mode],
427 SendGift => [text_parse_mode],
428 SendGiftChat => [text_parse_mode],
429 CopyMessage => [parse_mode],
432 PostStory => [parse_mode],
433 EditStory => [parse_mode],
434 EditEphemeralMessageText => [parse_mode],
435 EditEphemeralMessageCaption => [parse_mode],
436 SendPoll => [explanation_parse_mode, description_parse_mode],
437}
438
439impl VisitParseModes for AnswerInlineQuery {
440 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
441 self.results
442 .iter_mut()
443 .for_each(|result| visit_parse_modes_in_inline_query_result(result, &mut visitor))
444 }
445}
446
447impl VisitParseModes for AnswerWebAppQuery {
448 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
449 visit_parse_modes_in_inline_query_result(&mut self.result, &mut visitor);
450 }
451}
452
453impl VisitParseModes for SavePreparedInlineMessage {
454 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
455 visit_parse_modes_in_inline_query_result(&mut self.result, &mut visitor);
456 }
457}
458
459impl VisitParseModes for SendMediaGroup {
460 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
461 self.media
462 .iter_mut()
463 .for_each(|media| visit_parse_modes_in_input_media(media, &mut visitor))
464 }
465}
466
467impl VisitParseModes for EditMessageMedia {
468 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
469 visit_parse_modes_in_input_media(&mut self.media, &mut visitor);
470 }
471}
472
473impl VisitParseModes for EditMessageMediaInline {
474 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
475 visit_parse_modes_in_input_media(&mut self.media, &mut visitor);
476 }
477}
478
479impl VisitParseModes for EditEphemeralMessageMedia {
480 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
481 visit_parse_modes_in_input_media(&mut self.media, &mut visitor);
482 }
483}
484
485impl VisitParseModes for EditMessageChecklist {
486 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
487 visitor(&mut self.checklist.parse_mode);
488 }
489}
490
491impl VisitParseModes for SendChecklist {
492 fn visit_parse_modes(&mut self, mut visitor: impl FnMut(&mut Option<ParseMode>)) {
493 visitor(&mut self.checklist.parse_mode);
494 }
495}
496
497fn visit_parse_modes_in_inline_query_result(
498 result: &mut InlineQueryResult,
499 visitor: &mut impl FnMut(&mut Option<ParseMode>),
500) {
501 use InlineQueryResult::*;
502
503 let parse_mode = match result {
504 CachedAudio(r) => &mut r.parse_mode,
506 CachedDocument(r) => &mut r.parse_mode,
507 CachedGif(r) => &mut r.parse_mode,
508 CachedMpeg4Gif(r) => &mut r.parse_mode,
509 CachedPhoto(r) => &mut r.parse_mode,
510 CachedVideo(r) => &mut r.parse_mode,
511 CachedVoice(r) => &mut r.parse_mode,
512 Audio(r) => &mut r.parse_mode,
513 Document(r) => &mut r.parse_mode,
514 Gif(r) => &mut r.parse_mode,
515 Mpeg4Gif(r) => &mut r.parse_mode,
516 Photo(r) => &mut r.parse_mode,
517 Video(r) => &mut r.parse_mode,
518 Voice(r) => &mut r.parse_mode,
519
520 CachedSticker(r) => match &mut r.input_message_content {
522 Some(InputMessageContent::Text(t)) => &mut t.parse_mode,
523 _ => return,
524 },
525 Article(r) => match &mut r.input_message_content {
526 InputMessageContent::Text(t) => &mut t.parse_mode,
527 _ => return,
528 },
529 Contact(r) => match &mut r.input_message_content {
530 Some(InputMessageContent::Text(t)) => &mut t.parse_mode,
531 _ => return,
532 },
533 Location(r) => match &mut r.input_message_content {
534 Some(InputMessageContent::Text(t)) => &mut t.parse_mode,
535 _ => return,
536 },
537 Venue(r) => match &mut r.input_message_content {
538 Some(InputMessageContent::Text(t)) => &mut t.parse_mode,
539 _ => return,
540 },
541
542 Game(_r) => return,
544 };
545
546 visitor(parse_mode);
547}
548
549fn visit_parse_modes_in_input_media(
550 media: &mut InputMedia,
551 visitor: &mut impl FnMut(&mut Option<ParseMode>),
552) {
553 use InputMedia::*;
554
555 let parse_mode = match media {
556 Photo(m) => &mut m.parse_mode,
557 Video(m) => &mut m.parse_mode,
558 Animation(m) => &mut m.parse_mode,
559 Audio(m) => &mut m.parse_mode,
560 Document(m) => &mut m.parse_mode,
561 VoiceNote(m) => &mut m.parse_mode,
562 };
563
564 visitor(parse_mode);
565}