Telegram-бот ConversationHandler игнорирует резервные варианты

#python #python-telegram-bot

Вопрос:

У меня проблема с ботом Telegram (python-telegram-бот). Я сделал ConversationHandler, но «резервные варианты» не сработают. Бот просто игнорирует команду «/стоп «. Когда я отправляю «/стоп» , бот отправляет мне «Первый обработчик» вместо «До свидания». Что случилось?

 import os

import telegram
from telegram.ext import (ConversationHandler,
                          CommandHandler,
                          MessageHandler,
                          Filters,
                          Updater
)
from dotenv import load_dotenv

load_dotenv()

TELEGRAM_TOKEN = os.environ['TELEGRAM_TOKEN']
USER_ID = os.environ['USER_ID']
bot = telegram.Bot(token=TELEGRAM_TOKEN)
updater = Updater(token=TELEGRAM_TOKEN)


def start(update, context):
    context.bot.send_message(chat_id=update.effective_chat.id,
                             text='hi')
    return 1


def stop(update, context):
    context.bot.send_message('Good Bye')
    return ConversationHandler.END


def first_handler(update, context):
    context.bot.send_message(chat_id=update.effective_chat.id,
                             text='First handler')
    return 1


conv_handler = ConversationHandler(
    entry_points=[CommandHandler('Start', start)],
    states={
        1: [MessageHandler(Filters.text, first_handler,
                           pass_user_data=True)],
    },
    fallbacks=[CommandHandler('stop', stop)]
)

dispatcher = updater.dispatcher
dispatcher.add_handler(conv_handler)

updater.start_polling()
updater.idle()
 

Ответ №1:

Согласно документации, программа MessageHandler(Filters.text, ...) обрабатывает все текстовые сообщения, включая команду /stop. Однако резервные варианты срабатывают только в том случае, если ни один из вышеперечисленных обработчиков не смог обработать сообщение.

Вы можете исключить команды из обработчика сообщений:

 MessageHandler(
    Filters.text amp; (~ Filters.command),
    first_handler,
)
 

Синтаксис объединения фильтров описан здесь.

Комментарии:

1. Вы хотите добавить это исключение в <MessageHandler> в <MessageHandler><состояния>? К сожалению, это не сработает. «Неразрешенная ссылка на атрибут» Объединенный фильтр «для фильтров класса» «и» Неразрешенная ссылка на атрибут «Инвертированный фильтр» для фильтров класса» » ошибки

2. Я отредактировал свой ответ, вы использовали последнюю версию? Просто замените свой обработчик сообщений, как вы сказали.

3. Большое спасибо! Теперь это работает. Насколько я понимаю, мы просто исключили команды «/start», «/stop», «/что угодно» из обработчика сообщений для def. первый помощник? Верно?

4. Я хотел бы добавить, что pass_user_data это устарело и не будет иметь никакого эффекта, поскольку OP использует контекстный API, представленный в версии 12 PTB.

5. @Иван, это правильно. Вместо этого вы можете исключить одно сообщение «/стоп» только при использовании Filters.text amp; (~ Filters.text(["/stop"])) в качестве фильтра.