Как-то, очередным одиноким вечером, мне стало скучно и захотелось поговорить (Ох уж эти социальные потребности человеков). Что ж, пришлось сделать для этого бота.
Купились? Ха! На самом деле мне конечно же есть с кем поговорить (нет), просто тема с телеграмом и ботами обошла меня стороной, потому что у меня никогда не было аккаунта (не было надобности), а тут по работе приходится там “чатиться”, ну раз произошло такое, что я обзавёлся акком, значит пришла пора изучить “телегу” чуть лучше чем никак. Вообще, очень давно, в далёких 2000-ых я пользовался ICQ (исключительно по работе) и там я писал бота на перле; самый простой эхо-бот, который отвечал заранее вбитыми в него фразами. У этого бота было одно великое предназначение, жаль, что всё провалилось… ну да ладно, в сторону горькое прошлое, приступим к изучению матчасти!
С чего начать?
Конечно же с чтения RTFM, НО так как букоф много, а времени мало – смело кладём хер на доку по API и следуем step-by-step за аффтором пока он жжот.
И так, для приготовления бота нам понадобятся следующие ингредиенты:
- Centos 7
- python3. Ну типа, 2k18 на пороге, а через 2 года поддержка python2.7 будет окончена, пора нехотя переползать на третью ветку…
- python virtual env. К сожалению, centos7 ещё не готов к python3, а особенно скудные репозитории redhat, поэтому нам придётся тащить модули из гита/pip’ом, НО чтоб в хламьё не зафоршмачить всем этим говном систему; чтоб не бороться одним тоскливым вечером с неразрешаемыми зависимостями при обновлении; чтоб не сидеть с грустной миной перед монитором после того, как зависимости разрешили, но скрипты больше не работают; чтоб избежать всех этих и других факапов – мы будем использовать виртуальные окружения змеюки.
- pytelegrambotapi. Собсно, это либа для общения с telegram api коих херова тонна и, вобщем-то, можно даже без неё обойтись, но-о-о как я уже писал ранее – букаф много, времени мало, и поэтому я делегирую транспорт опытным программистам, авторам модуля, которые знают как лучше наладить общение между ботом и api.
Вобщем-то это всё, ну не исключая конечно же холодной головы, горячего сердца, здравого рассудка и щепотки фантазии. Приступим!
Понеслася!
Перво-наперво, нам понадобится зарегистрировать бота в telegram. В отличии от ICQ, в telegram есть очень чёткая грань между аккаунтами для людей, и аккаунтами для ботов. Заходим под своим аккаунтом а телегу как Вам это удобно: будь то веба, или клиент, – это не имеет значения; и ищем там вот этого товарища: @BotFather – это официальный бот telegram inc. для управления другими, пользовательскими ботами. Начинаем с ним беседу кнопкой “Start!” и следуя его подсказкам регистрируем себе бота, это очень просто и букаф там не оч много, вы справитесь, я в вас верю! Результатом вашей беседы с батей должен стать токен (Пример: 0123456789:AAAAA-hsnheHG3nBSbv2MM23bsallOpwkes
) по которому будет авторизоваться ваш бот. Записываем его куда-нить чтоб не забыть и переходим к настройке серверного окружения.
На сервере с Centos7 нам понадобится epel-repo где пакеты чуть посвежей чем в base (Но запашок от них тем не менее тот ещё).
yum install epel-release
Далее нам понадобится пакет python34-devel.x86_64
в составе которого, помимо прочего нам ненужного хлама, есть тот самый pyenv о котором я писал ранее в ингредиентах и pip при помощи которого мы поставим нужный нам модуль для общения с api telegramm.
yum install python34-devel.x86_64
Создаём директорию в которой будут храниться ваши вирутальные окружения в расчёте: один скрипт – одно окружение.
mkdir -p /usr/local/sbin/venvs && cd "$_"
Мы создали общую для вирутальных окружений директорию venvs и командой cd "$_"
мы перешли в эту директорию.
Теперь необходимо создать виртуальный домик для нашего бота.
pyvenv-3.4 telebot
В результате команды будет создана директория telebot с кучей дочерних директорий для модулей и библиотек. Заходим в эту директорию (cd telebot) и активируем виртуальное окружение (если надо, то деактивировать его можно командой deactivate
).
source bin/activate
После чего видим изменившуюся строку приглашения
(telebot) root /usr/local/sbin/venvs/telebot #
Если всё так – поздравляю! Вы ещё не накосячили и всё, как поговаривал товарищ Летов, идёт по-плану. Мы в виртуальном окружении, в котором можно извращаться над питоном и его модулями – как угодно: Ставить через yum, обновлять через pip, удалять/подменять либы – всё, что стыдно делать при приличных людях.
Теперь переходим если не к самомму главному, то ко второму по значимости пункту – установка модуля для общения с api telegram.
pip install --upgrade pip pip install pytelegrambotapi
Первой командой мы обновим pip, второй – поставим необходимый модуль. Проверяем всё ли мы сделали правильно:
python
Python 3.4.5 (default, May 29 2017, 15:17:55) [GCC 4.8.5 20150623 (Red Hat 4.8.5-11)] on linux Type "help", "copyright", "credits" or "license" for more information. >>>
>>> import pytelegrambotapi >>>
Если нет ошибок – вы настоящий программист! (нет) Так бы вам сказали на каком-нить курсе geekbrains, лишь бы платили бабло…
Выходим из интерпретатора python нажатием сочетания клавиш Ctrl+D
и создаём сам скрипт (любым текстовым редактором, у меня это nano (yum install nano
))
mkdir body && nano body/bot.py
Записываем туда код простейшего эхо-бота
#!/usr/bin/python3 import os import telebot import logging TOKEN = os.environ['TELETOKEN'] bot = telebot.TeleBot(TOKEN) logger = telebot.logger telebot.logger.setLevel(logging.DEBUG) @bot.message_handler(commands=['help', 'start']) def send_welcome(message): bot.reply_to(message, """\ Hi there, I am EchoBot.\ I am here to echo your kind words back to you.\ Just say anything nice and I'll say the exact same thing to you!\ """) @bot.message_handler(content_types=["text"]) def repeat_all_messages(message): bot.send_message(message.chat.id, message.text) bot.polling(none_stop=True)
Внимательный мамкин программист наверное скажет “Ха! Автомеханик лошара, а токен бота-то просрал! Фу таким быть!” и отчасти будет прав… пока что строку TOKEN = os.environ['TELETOKEN']
замените на TOKEN = 'ТУТ_ТОКЕН_БОТА_КОТОРЫЙ_ДАЛ_БАТЯ'
, а зачем у меня в примере сделано именно так – узнаете позже.
Теперь можно проверить работу скрипта запустив его:
python3 body/bot.py
Ответ должен быть примерно таким
2017-11-04 15:52:47,905 (__init__.py:269 MainThread) INFO - TeleBot: "Started polling." 2017-11-04 15:52:47,906 (util.py:55 PollingThread) DEBUG - TeleBot: "Received task" 2017-11-04 15:52:47,906 (apihelper.py:45 PollingThread) DEBUG - TeleBot: "Request: method=get url=https://api.telegram.org/bot0123456789:AAAAA-hsnheHG3nBSbv2MM23bsallOpwkes/getUpdates params={'offset': 1, 'timeout': 20} files=None" 2017-11-04 15:53:08,321 (apihelper.py:55 PollingThread) DEBUG - TeleBot: "The server returned: 'b'{"ok":true,"result":[]}''" 2017-11-04 15:53:08,322 (__init__.py:195 PollingThread) DEBUG - TeleBot: "Received 0 new updates"
Если всё так – можете в телеграме, от своего аккаунта, написать ему что-нибудь и он будет вам отвечать на команды /start
и /help
текстом, что записали в скрипте, а всё прочее просто будет копировать вам в ответ.
Собсно, на этом можно было бы и закончить, но тема сисек systemd не раскрыта.
Зачем нам это?
Можно было бы конечно создать виртуальное окружение у себя в хомяке и запускать это вручную, но-о-о-о я не из этих. Давайте попробуем написать unit-файл для systemd и делегировать ему запуск, поддержку “на лету” и завершение бота, в общем, отдадим ему управление.
Для начала поправим скрипт бота заменив TOKEN = 'ТУТ_ТОКЕН_БОТА_КОТОРЫЙ_ДАЛ_БАТЯ'
на то что там было изначально TOKEN = os.environ['TELETOKEN']
, затем нам понадобится написать один файл /etc/systemd/system/venv-telebot.service
. В директории /etc/systemd/system/
следует размещать самописные юниты; в /usr/lib/systemd/system/
обычно располагаются юниты распакованные из RPM-пакетов при установке, и в /run/systemd/system/
работающие в риалтайме. Называть его можно как угодно, но оканчиваться название должно на .service
– так мы дадим системе понять что это юнит, а не насрано. Помещаем туда содержимое:
[Unit] Description=Telegram bot written on python 3.4 and executed at python virtual env After=syslog.target network.target [Service] Type=simple User=nobody Group=nobody WorkingDirectory=/usr/local/sbin/venvs/telebot ExecStart=/usr/local/sbin/venvs/telebot/bin/python3 body/bot.py Restart=on-abort Environment=VIRTUAL_ENV=/usr/local/sbin/venvs/telebot Environment=TELETOKEN=AAAAA-hsnheHG3nBSbv2MM23bsallOpwkes Environment=PATH=$VIRTUAL_ENV/bin:$PATH [Install] WantedBy=multi-user.target
Где
- Description – Просто описание сервиса.
- After – указание на то, после каких служб надо запускать сервис.
- Type – Тип, где simple по-умолчанию предполагает, что служба будет запущена незамедлительно. Процесс при этом не должен разветвляться. Не следует использовать этот тип, если другие службы зависят от очередности при запуске данной службы.
- User и Group – юзер/группа от имени которых будет запущен сервис. Безопасность и все дела 🙂
- WorkingDirectory – текущий каталог становится таковым при запуске сервиса.
- ExecStart – команда запускающая сервис.
- Restart – Рестартуем при неправильном завершении сервиса.
- Environment – некие настройки окружения передаваемые при старте. Именно сюда мы помещаем токен нашего бота. Опять же для безопасности. Благодаря такому подходу, писав 100500 часов подряд своего супер-пупер бота, с квадратными, красными глазами, вы можете свободно пушить скрипт в гит, будучи уверенным, что там нет токенов, паролей и т.п.
- WantedBy – уроверь запуска, в котором multi-user.target соответствует привычному runlevel=3
Финальным штрихом нашего кулинарно-админского безумия будет
systemctl enable venv-telebot.service
для “автозагрузки” нашего бота и запуск последнего командой
systemctl start venv-telebot.service
Ну вот, собсно, и всё. Больше рабочих примеров из коробки есть в репе модуля. С вами был я – автомеханик-социопат и мой робот служивший примером @Alpha_the_bot. До новых встреч! ^_^
Спасибо за статью!
Только команда для проверки должна быть “>>> import telebot”, а не “import pytelegrambotapi”))
Устарел гайд. Telebot теперь работает на Python 3.7 и выше