Уведомления

Группа в Telegram: @pythonsu

#1 Ноя. 20, 2022 17:26:26

weber
Зарегистрирован: 2022-11-20
Сообщения: 2
Репутация: +  0  -
Профиль   Отправить e-mail  

проблема с обработкой команд с аргументами в боте для телеграм

Всем доброго времени суток! Решил поучить “питон” и первый учебный свой проект решил посвятить написанию бота в “телегу”. После PHP (где таких проблем нет) мне тут головной боли добавил синтаксис (отступы и т.д.), на которые среда кодинга (PyCharm) ругается порой по “черному”… Но с этим я вроде справляюсь, суть в другом.

Я решил сделать в коде обработчик команд для бота с аргументами, в качестве первой такой команды выбрал возможность выводить случайное число из указанного диапазона чисел, по типу:

/rand 1 500

из чего понятно, что я говорю боту выдать случайное число в диапазоне от 1 до 500, при этом скрипт должен обработать введенные данные и понять, правильный формат команды или нет. если аргументы не являются числами или вовсе не введены, то бот должен ответить, что команда введена не верно.
Скрипт в принципе работает(когда ввожу команду верно), но если я неправильно укажу команду (без аргументов или это не цифры и т.д.),то получается с ошибкой, которая приводит к крашу скрипта…

 IndexError: list index out of range

т.е. ругается на строчку с:
 x_min = int(message.text.split()[1])

уже мозг сломал, не могу понять в чем дело…

вот сам код полностью:

 import telebot
import random
API_BOT = "бота токен"
ADMIN_USER_ID: list[int] = [мой айди в телеге]
THIS_BOT = telebot.TeleBot(API_BOT)
@THIS_BOT.message_handler(commands=['start'])
def cmd_start(message):
    THIS_BOT.send_message(message.chat.id,
                          f'<b>Привет, {message.from_user.first_name}! Я Ваш интерактивный помошник.</b>',
                          parse_mode='html')
@THIS_BOT.message_handler(commands=['rand'])
def cmd_rand(message):
    x_min = int(message.text.split()[1])
    x_max = int(message.text.split()[2])
    if x_min < x_max:
        result = random.randint(x_min, x_max)
        THIS_BOT.send_message(message.chat.id, f"Случайное число: {result} ", parse_mode='html')
    else:
        THIS_BOT.send_message(message.chat.id, f"Ошибка! Неправильно указаны аргументы команды. \n Вы написали "
                                               f"следующее: /rand {x_min} {x_max}", parse_mode='html')
@THIS_BOT.message_handler()
def msg(message):
    if (message.text == "debug_info") and (message.from_user.id in ADMIN_USER_ID) is True:
        THIS_BOT.send_message(message.chat.id, message, parse_mode='html')
if __name__ == "__main__":
    THIS_BOT.polling(none_stop=True)

Отредактировано weber (Ноя. 20, 2022 17:27:39)

Офлайн

#2 Ноя. 20, 2022 18:49:01

weber
Зарегистрирован: 2022-11-20
Сообщения: 2
Репутация: +  0  -
Профиль   Отправить e-mail  

проблема с обработкой команд с аргументами в боте для телеграм

нашел решение, которое помогло корректно работать обработчику команды, не знаю насколько это правильно, но как то так.. вот код:

 import telebot
import random
API_BOT = "токен бота"
ADMIN_USER_ID: list[int] = [айди пользователя бота-админа]
THIS_BOT = telebot.TeleBot(API_BOT)
@THIS_BOT.message_handler(commands=['start'])
def cmd_start(message):
    THIS_BOT.send_message(message.chat.id,
                          f'<b>Привет, {message.from_user.first_name}! Я Ваш интерактивный помошник.</b>',
                          parse_mode='html')
@THIS_BOT.message_handler(commands=['rand'])
def cmd_rand(message):
    if len(message.text.split()[1:]) == 2:
        x_min = int(message.text.split()[1])
        x_max = int(message.text.split()[2])
    else:
        x_min = 0
        x_max = 0
    if x_min and x_max != 0:
        result = random.randint(x_min, x_max)
        THIS_BOT.send_message(message.chat.id, f"Случайное число: {result} ", parse_mode='html')
    else:
        THIS_BOT.send_message(message.chat.id, f"Ошибка! Неправильно указаны аргументы команды. \n Правильный пример: "
                                               f"/rand 1 100 \n Вы написали следующее: {message.text}", parse_mode='html')
@THIS_BOT.message_handler()
def msg(message):
    if (message.text == "debug_info") and (message.from_user.id in ADMIN_USER_ID) is True:
        THIS_BOT.send_message(message.chat.id, message, parse_mode='html')
if __name__ == "__main__":
    THIS_BOT.polling(none_stop=True)

Как видно из положения вышел, проверяя количество элементов внутри массива, если их там реально не столько, сколько должно быть, то бот отвечает, советуя исправить формат ввода команды. Теперь другая проблема, корректно проверять, что это не текст, а числа.

Офлайн

#3 Ноя. 20, 2022 22:46:02

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 9867
Репутация: +  853  -
Профиль   Отправить e-mail  

проблема с обработкой команд с аргументами в боте для телеграм

weber
Решил поучить “питон”
Тебе надо не столько язык учить какой-то новый, сколько само программирование доязыковое. Знаешь, да, что такое псевдокод? Вот тебе надо сначала на псевдокоде учиться писать. К счастью, питон очень приближен к псевдокоду, поэтому он как раз в роли псевдокода и выступит.

weber
После PHP (где таких проблем нет)
Проблема PHPшников в том, что у них складывается одинаковое мышление, которое сильно тупообразное. Поэтому в своей среде они чувствуют себя наверху горы и могут годами там классно писать всё, но когда они попадают в другие языки типа компилируемых, это их мышление просто оказывается непригодным и им надо учиться всему заново.

PHP даёт тебе возможность быть тупым и при этом чувствовать себя достойно, и это может сохраняться годами. Но вот переход на другой язык становится большой проблемой. В других языках нужно более умное и тонкое мышление, которое в PHP практически не развивается.

weber
нашел решение, которое помогло корректно работать обработчику команды, не знаю насколько это правильно
Ты бы на псевдокоде сначала написал бы очень конкретно, что тебе нужно получить в конечном итоге, так оно было бы оптимально, а потом бы ты это переписал уже на питон и всё бы получилось сразу.

Надо было записать так:
  
x_min = x_max = None
 
text = message.text
chatid = message.chat.id
 
args = text.split()[1:]
if len(args) != 2:
    bot.send_message(chatid, 'Error: should be two arguments')
    return
 
try:
    x_min = int(args[0])
except ValueError:
    pass
 
try:
    x_max = int(args[1])
except ValueError:
    pass
 
if x_min is None:
    bot.send_message(chatid, 'Error: can\'t read min argument')
    return
if x_max is None:
    bot.send_message(chatid, 'Error: can\'t read max argument')
    return
 
if x_min == 0:
    bot.send_message(chatid, 'Error: zero min argument')
    return
if x_max == 0:
    bot.send_message(chatid, 'Error: zero max argument')
    return
 
bot.send_message(
    chatid,
    'Ok. See min argument {} and max argument {}'.format(
        x_min, x_max)
)
Как видишь, в моём коде, после того как он пройден интерпретатором, не осталось сомнений, что в нём что-то пропущено или что-то упущено. Каждая проверка дала свой результат и сразу отмерла. Также в нём всегда можно внедриться посередине (в любой точке кода) и вставить дополнительную проверку, ничего не разделяя, потому что всё разделено заранее как раз для этого. Благодаря этому код можно писать послойно. Написал слой, отладил его, всё работает; после этого поверх этого слоя снова пишешь слой, отлаживаешь его и всё работает. И так ты послойно приводишь программу к крепкому виду. При этом тебе не надо её переделывать по сто раз в разных фрагментах, ты её просто дописываешь, дописываешь, дописываешь.

Вот это всё вырабатывается, когда учишься реальному программированию, проходя все классические этапы обучения. Надо уметь и словесно описывать программу, и на блок-схемах описывать программу, и на псевдокоде её записывать разными способами (псевдокод тоже бывает разный, различается по уровням детализации), и в разных стилях всё это писать. Сначала ты всё это пишешь, потом это всё постепенно формируется прямо в мозгах и ты только в воображении всё это пишешь. Так ты приходишь к тому, что программы ты пишешь прямо в голове, когда по улице идёшь и гуляешь, а на компе ты их потом просто записываешь, переписывая их готовые из головы в комп.



Отредактировано py.user.next (Ноя. 20, 2022 22:59:58)

Офлайн

Board footer

Модераторировать

Powered by DjangoBB

Lo-Fi Version