Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 27 additions & 4 deletions telegram/_bot.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
import logging
import pickle
from contextlib import AbstractAsyncContextManager
from copy import copy
from datetime import datetime
from types import TracebackType
from typing import (
Expand Down Expand Up @@ -346,10 +347,16 @@ def _insert_defaults(self, data: Dict[str, object]) -> None: # skipcq: PYL-R020
for key, val in data.items():
# 1)
if isinstance(val, InputMedia):
# Copy object as not to edit it in-place
val = copy(val)
val.parse_mode = DefaultValue.get_value(val.parse_mode)
data[key] = val
elif key == "media" and isinstance(val, list):
for media in val:
# Copy objects as not to edit them in-place
copy_list = [copy(media) for media in val]
for media in copy_list:
media.parse_mode = DefaultValue.get_value(media.parse_mode)
data[key] = copy_list
# 2)
else:
data[key] = DefaultValue.get_value(val)
Expand Down Expand Up @@ -2852,24 +2859,39 @@ def _effective_inline_results( # skipcq: PYL-R0201
return effective_results, next_offset

@no_type_check # mypy doesn't play too well with hasattr
def _insert_defaults_for_ilq_results(self, res: "InlineQueryResult") -> None:
def _insert_defaults_for_ilq_results(self, res: "InlineQueryResult") -> "InlineQueryResult":
"""The reason why this method exists is similar to the description of _insert_defaults
The reason why we do this in rather than in _insert_defaults is because converting
DEFAULT_NONE to NONE *before* calling to_dict() makes it way easier to drop None entries
from the json data.

Must return the correct object instead of editing in-place!
"""
# Copy the objects that need modification to avoid modifying the original object
copied = False
if hasattr(res, "parse_mode"):
res = copy(res)
copied = True
res.parse_mode = DefaultValue.get_value(res.parse_mode)
if hasattr(res, "input_message_content") and res.input_message_content:
if hasattr(res.input_message_content, "parse_mode"):
if not copied:
res = copy(res)
copied = True
res.input_message_content = copy(res.input_message_content)
res.input_message_content.parse_mode = DefaultValue.get_value(
res.input_message_content.parse_mode
)
if hasattr(res.input_message_content, "disable_web_page_preview"):
if not copied:
res = copy(res)
res.input_message_content = copy(res.input_message_content)
res.input_message_content.disable_web_page_preview = DefaultValue.get_value(
res.input_message_content.disable_web_page_preview
)

return res

@_log
async def answer_inline_query(
self,
Expand Down Expand Up @@ -2968,8 +2990,9 @@ async def answer_inline_query(
)

# Apply defaults
for result in effective_results:
self._insert_defaults_for_ilq_results(result)
effective_results = [
self._insert_defaults_for_ilq_results(result) for result in effective_results
]

data: JSONDict = {"inline_query_id": inline_query_id, "results": effective_results}

Expand Down
21 changes: 19 additions & 2 deletions telegram/ext/_extbot.py
Original file line number Diff line number Diff line change
Expand Up @@ -370,11 +370,17 @@ def _insert_defaults(self, data: Dict[str, object]) -> None:

# 3)
elif isinstance(val, InputMedia) and val.parse_mode is DEFAULT_NONE:
# Copy object as not to edit it in-place
val = copy(val)
val.parse_mode = self.defaults.parse_mode if self.defaults else None
data[key] = val
elif key == "media" and isinstance(val, list):
for media in val:
# Copy objects as not to edit them in-place
copy_list = [copy(media) for media in val]
for media in copy_list:
if media.parse_mode is DEFAULT_NONE:
media.parse_mode = self.defaults.parse_mode if self.defaults else None
data[key] = copy_list

def _replace_keyboard(self, reply_markup: Optional[ReplyMarkup]) -> Optional[ReplyMarkup]:
# If the reply_markup is an inline keyboard and we allow arbitrary callback data, let the
Expand Down Expand Up @@ -546,29 +552,40 @@ def _effective_inline_results(
return results, next_offset

@no_type_check # mypy doesn't play too well with hasattr
def _insert_defaults_for_ilq_results(self, res: "InlineQueryResult") -> None:
def _insert_defaults_for_ilq_results(self, res: "InlineQueryResult") -> "InlineQueryResult":
"""This method is called by Bot.answer_inline_query to replace `DefaultValue(obj)` with
`obj`.
Overriding this to call insert the actual desired default values.
"""
# Copy the objects that need modification to avoid modifying the original object
copied = False
if hasattr(res, "parse_mode") and res.parse_mode is DEFAULT_NONE:
res = copy(res)
copied = True
res.parse_mode = self.defaults.parse_mode if self.defaults else None
if hasattr(res, "input_message_content") and res.input_message_content:
if (
hasattr(res.input_message_content, "parse_mode")
and res.input_message_content.parse_mode is DEFAULT_NONE
):
if not copied:
res = copy(res)
copied = True
res.input_message_content.parse_mode = (
self.defaults.parse_mode if self.defaults else None
)
if (
hasattr(res.input_message_content, "disable_web_page_preview")
and res.input_message_content.disable_web_page_preview is DEFAULT_NONE
):
if not copied:
res = copy(res)
res.input_message_content.disable_web_page_preview = (
self.defaults.disable_web_page_preview if self.defaults else None
)

return res

async def stop_poll(
self,
chat_id: Union[int, str],
Expand Down
Loading