Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

#2764; Implemented "prefallbacks" feature#2960

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to ourterms of service andprivacy statement. We’ll occasionally send you account related emails.

Already on GitHub?Sign in to your account

Closed
david-shiko wants to merge1 commit intopython-telegram-bot:masterfromdavid-shiko:prefallbacks
Closed
Changes fromall 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
128 changes: 73 additions & 55 deletionstelegram/ext/conversationhandler.py
View file
Open in desktop
Original file line numberDiff line numberDiff line change
Expand Up@@ -50,11 +50,11 @@ class _ConversationTimeoutContext:
__slots__ = ('conversation_key', 'update', 'dispatcher', 'callback_context')

def __init__(
self,
conversation_key: Tuple[int, ...],
update: Update,
dispatcher: 'Dispatcher',
callback_context: Optional[CallbackContext],
self,
conversation_key: Tuple[int, ...],
update: Update,
dispatcher: 'Dispatcher',
callback_context: Optional[CallbackContext],
):
self.conversation_key = conversation_key
self.update = update
Expand DownExpand Up@@ -126,6 +126,13 @@ class ConversationHandler(Handler[Update, CCT]):
trigger the start of the conversation. The first handler which :attr:`check_update`
method returns :obj:`True` will be used. If all return :obj:`False`, the update is not
handled.
prefallbacks (List[:class:`telegram.ext.Handler`]): A list of handlers that will be trigger
before all the other "states" and "fallbacks" handlers. Useful for such commands as
"cancel", "back", "repeat". Intended to place part of "fallbacks" handlers inside and
avoid using many "& ~" conditions in "Filters".
:obj:`False` on :attr:`check_update`. The first handler which :attr:`check_update`
method returns :obj:`True` will be used. If all return :obj:`False`, the update will be
forwarded to "states" handlers.
states (Dict[:obj:`object`, List[:class:`telegram.ext.Handler`]]): A :obj:`dict` that
defines the different states of conversation a user can be in and one or more
associated ``Handler`` objects that should be used in that state. The first handler
Expand DownExpand Up@@ -213,25 +220,28 @@ class ConversationHandler(Handler[Update, CCT]):
WAITING: ClassVar[int] = -3
""":obj:`int`: Used as a constant to handle state when a conversation is still waiting on the
previous ``@run_sync`` decorated running handler to finish."""

# pylint: disable=W0231
def __init__(
self,
entry_points: List[Handler[Update, CCT]],
states: Dict[object, List[Handler[Update, CCT]]],
fallbacks: List[Handler[Update, CCT]],
allow_reentry: bool = False,
per_chat: bool = True,
per_user: bool = True,
per_message: bool = False,
conversation_timeout: Union[float, datetime.timedelta] = None,
name: str = None,
persistent: bool = False,
map_to_parent: Dict[object, object] = None,
run_async: bool = False,
self,
entry_points: List[Handler[Update, CCT]],
states: Dict[object, List[Handler[Update, CCT]]],
fallbacks: List[Handler[Update, CCT]],
prefallbacks: List[Handler[Update, CCT]] = None,
allow_reentry: bool = False,
per_chat: bool = True,
per_user: bool = True,
per_message: bool = False,
conversation_timeout: Union[float, datetime.timedelta] = None,
name: str = None,
persistent: bool = False,
map_to_parent: Dict[object, object] = None,
run_async: bool = False,
):
self.run_async = run_async

self._entry_points = entry_points
self._prefallbacks = prefallbacks or []
self._states = states
self._fallbacks = fallbacks

Expand DownExpand Up@@ -266,6 +276,7 @@ def __init__(
)

all_handlers: List[Handler] = []
all_handlers.extend(prefallbacks) # type: ignore[arg-type]
all_handlers.extend(entry_points)
all_handlers.extend(fallbacks)

Expand DownExpand Up@@ -324,6 +335,18 @@ def entry_points(self) -> List[Handler]:
def entry_points(self, value: object) -> NoReturn:
raise ValueError('You can not assign a new value to entry_points after initialization.')

@property
def prefallbacks(self) -> List[Handler]:
"""List[:class:`telegram.ext.Handler`]: A list of handlers that will be
checked for handling before all the other handlers
:obj:`False` on :attr:`check_update`.
"""
return self._prefallbacks # pylint: disable=maybe-no-member

@prefallbacks.setter
def prefallbacks(self, value: object) -> NoReturn:
raise ValueError('You can not assign a new value to prefallbacks after initialization.')

@property
def states(self) -> Dict[object, List[Handler]]:
"""Dict[:obj:`object`, List[:class:`telegram.ext.Handler`]]: A :obj:`dict` that
Expand DownExpand Up@@ -386,7 +409,7 @@ def per_message(self, value: object) -> NoReturn:

@property
def conversation_timeout(
self,
self,
) -> Optional[Union[float, datetime.timedelta]]:
""":obj:`float` | :obj:`datetime.timedelta`: Optional. When this
handler is inactive more than this timeout (in seconds), it will be automatically
Expand DownExpand Up@@ -483,12 +506,12 @@ def _resolve_promise(self, state: Tuple) -> object:
return res

def _schedule_job(
self,
new_state: object,
dispatcher: 'Dispatcher',
update: Update,
context: Optional[CallbackContext],
conversation_key: Tuple[int, ...],
self,
new_state: object,
dispatcher: 'Dispatcher',
update: Update,
context: Optional[CallbackContext],
conversation_key: Tuple[int, ...],
) -> None:
if new_state != self.END:
try:
Expand DownExpand Up@@ -565,41 +588,36 @@ def check_update(self, update: object) -> CheckUpdateType: # pylint: disable=R0
check = entry_point.check_update(update)
if check is not None and check is not False:
handler = entry_point
break

else:
if state is None:
return None
return key, handler, check
# Find a prefallback handler before all others handlers
for prefallback in self.prefallbacks:
check = prefallback.check_update(update)
if check is not None and check is not False:
handler = prefallback
return key, handler, check

# Get the handler list for current state, if we didn't find one yet and we're still here
if state is not None and not handler:
handlers = self.states.get(state)

for candidate in handlers or []:
check = candidate.check_update(update)
if check is not None and check is not False:
handler = candidate
break

# Find a fallback handler if all other handlers fail
else:
for fallback in self.fallbacks:
check = fallback.check_update(update)
if check is not None and check is not False:
handler = fallback
break

else:
return None
handlers = self.states.get(state)
for candidate in handlers or []:
check = candidate.check_update(update)
if check is not None and check is not False:
handler = candidate
return key, handler, check

return key, handler, check # type: ignore[return-value]
# Find a fallback handler if all other handlers fail
for fallback in self.fallbacks:
check = fallback.check_update(update)
if check is not None and check is not False:
handler = fallback
return key, handler, check
return None

def handle_update( # type: ignore[override]
self,
update: Update,
dispatcher: 'Dispatcher',
check_result: CheckUpdateType,
context: CallbackContext = None,
self,
update: Update,
dispatcher: 'Dispatcher',
check_result: CheckUpdateType,
context: CallbackContext = None,
) -> Optional[object]:
"""Send the update to the callback for the current state and Handler

Expand Down

[8]ページ先頭

©2009-2025 Movatter.jp