Как перезапустить бота кодом, при нажатии inline кнопки(pytelegrambotapi)?
Есть Telegram бот, код:
import telebot
from telebot import types
bot = telebot.TeleBot("*****")
@bot.message_handler(commands=["start"])
def send_welcome(message):
global markup, DELETEuserName, DELETEuserName1 #делаю переменную глобальной, чтобы она была видна в остальных функциях. Переменные с приставкой DELETE нужны для того, чтобы удалить сообщения от бота
markup = types.InlineKeyboardMarkup()
resetDataKey = types.InlineKeyboardButton("Сбросить", callback_data="resetData")
markup.add(resetDataKey)
userName = bot.send_message(message.chat.id, "Здравствуйте, введите имя")
DELETEuserName = userName.chat.id
DELETEuserName1 = userName.message_id
bot.register_next_step_handler(userName, userSurNameFUNC)
def userSurNameFUNC(message):
userName1 = message.text
global userName, DELETEuserSurName, DELETEuserSurName1 #проделываю эту махинацию, чтобы сообщения превращались в тип String и конкатенировались
userName = userName1
userSurName = bot.send_message(message.chat.id, "Теперь введите фамилию", reply_markup=markup)
DELETEuserSurName = userSurName.chat.id
DELETEuserSurName1 = userSurName.message_id
bot.delete_message(message.chat.id, message.message_id)
bot.delete_message(DELETEuserName, DELETEuserName1)
bot.register_next_step_handler(userSurName, endProgrammFUNC)
def endProgrammFUNC(message):
userSurName1 = message.text
global userSurName, DELETEendProgramm, DELETEendProgramm1
userSurName = userSurName1
endProgramm = bot.send_message(message.chat.id, "Вас зовут " + userName + " " + userSurName)
DELETEendProgramm = endProgramm.chat.id
DELETEendProgramm1 = endProgramm.message_id
bot.delete_message(message.chat.id, message.message_id)
bot.delete_message(DELETEuserSurName, DELETEuserSurName1)
@bot.callback_query_handler(func=lambda call: True)
def inline_handler(call):
if call.data == "resetData":
bot.delete_message(call.message.chat.id, call.message.message_id)
userName = bot.send_message(call.message.chat.id, "Здравствуйте, введите имя")
DELETEuserName = userName.chat.id
DELETEuserName1 = userName.message_id
try:
try:
pass
except:
try:
bot.delete_message(DELETEuserSurName, DELETEuserSurName1)
except:
bot.delete_message(DELETEendProgramm, DELETEendProgramm1)
except:
pass
bot.register_next_step_handler(userName, userSurNameFUNC)
bot.infinity_polling()
Когда я запускаю бота, с первого раза всё работает стабильно, но когда я нажимаю сбросить, и хочу начать по новой (начать вводить имя), то бот работает по предыдущему запросу, и думает что я ввёл фамилию.
Соответственно сначала бот пишет "Введите имя", а потом он думает что я ввожу фамилию, и выдаёт результат "Вас зовут" + имя и фамилия введённая пользователем, затем такую ошибку:
2021-10-31 21:53:34,798 (__init__.py:663 MainThread) ERROR - TeleBot: "A request
to the Telegram API was unsuccessful. Error code: 400. Description: Bad Request
: message to delete not found"
Как можно при нажатии inline кнопки сбросить работу программы, перезапустить бота и начать сначала? Чтобы при каждом нажатии на inline кнопку, скрипт будто закрыли и открыли заново. Не знаю как сделать это кодом, чтобы бот работал без остановки 24/7.
Ответы (1 шт):
Можно повторно вызывать функцию send_welcome прямо из inline_handler, которая ловит нажатие кнопки сброса.
А в самой функции send_welcome сбрасывать все зарегистрированные обработчики с помощью вызова bot.clear_step_handler(message).
Тогда если send_welcome вызвана первый раз, никаких обработчиков еще не установлено и ничего не произойдет, а если повторно - они будут сброшены, как и требуется.
Вот пример рабочего кода:
@bot.message_handler(commands=["start"])
def send_welcome(message):
global DELETEuserName1
bot.clear_step_handler(message)
userName = bot.send_message(message.chat.id, "Здравствуйте, введите имя")
DELETEuserName1 = userName.message_id
bot.register_next_step_handler(userName, userSurNameFUNC)
def userSurNameFUNC(message):
global userName, DELETEuserSurName, DELETEuserSurName1
userName = message.text
markup = types.InlineKeyboardMarkup()
resetDataKey = types.InlineKeyboardButton("Сбросить", callback_data="resetData")
markup.add(resetDataKey)
userSurName = bot.send_message(message.chat.id, "Теперь введите фамилию", reply_markup=markup)
DELETEuserSurName = userSurName.chat.id
DELETEuserSurName1 = userSurName.message_id
bot.delete_message(message.chat.id, message.message_id)
bot.delete_message(message.chat.id, DELETEuserName1)
bot.register_next_step_handler(userSurName, endProgrammFUNC)
def endProgrammFUNC(message):
global userSurName, DELETEendProgramm, DELETEendProgramm1
userSurName = message.text
endProgramm = bot.send_message(message.chat.id, "Вас зовут " + userName + " " + userSurName)
DELETEendProgramm = endProgramm.chat.id
DELETEendProgramm1 = endProgramm.message_id
bot.delete_message(message.chat.id, message.message_id)
bot.delete_message(DELETEuserSurName, DELETEuserSurName1)
@bot.callback_query_handler(func=lambda call: True)
def inline_handler(call):
if call.data == "resetData":
bot.delete_message(call.message.chat.id, call.message.message_id)
send_welcome(call.message)
bot.infinity_polling()