Telegram bot, взаимодействующий с API OpenAI без проксирования. Разработка на Python

Создадим бота, использующего API OpenAI. И так развернем его на сервере, чтобы не настраивать проксирование запросов к API OpenAI (который заблокирован для пользователей из России), и не использовать иностранные VPS.

Бот должен помогать осуществлять

  • Автоматизацию рутинных задач (написание кода, документации, тестов).

  • Предоставлять рекомендации и примеры кода.

  • Анализировать код, находить ошибки и давать предложения по улучшению.

  • Сокращать времени разработки и тестирования.

Планирование и дизайн бота

Функциональные требования:

  1. Приветственное сообщение при запуске.

  2. Генерация ответов через OpenAI API.

  3. Обработка команд, например, /bot или /start

  4. Логирование ошибок.

  5. Автоматическое повторное подключение при сбое.

Основные сценарии использования

  1. Запуск бота:

  2. Запрос информации:

    • Пользователь отправляет команду /bot или любое текстовое сообщение.

    • Бот генерирует ответ с помощью OpenAI API и отправляет его пользователю.

  3. Обработка ошибок:

Выбор технологий и инструментов

Мы будем использовать следующие технологии и инструменты:

  • Python: Простота и легкость в изучении, большое количество библиотек и инструментов.

  • TeleBot: Простой интерфейс для взаимодействия с Telegram API.

  • OpenAI API: Использование модели GPT-3.5 для генерации текстовых ответов.

Написание кода телеграм-бота

Бот включает в себя несколько ключевых компонентов, которые обеспечивают его функциональность и взаимодействие с пользователями:

  1. Telegram Bot API: Этот компонент отвечает за прием и отправку сообщений пользователям через платформу Telegram.

  2. OpenAI API: Используется для генерации ответов на запросы пользователей с помощью модели GPT-3.5.

  3. Логирование: Ведет запись событий и ошибок для последующего анализа и отладки.

  4. Основной цикл (Event Loop): Обеспечивает непрерывную работу бота и обработку всех входящих сообщений.

Эти компоненты взаимодействуют следующим образом:

  • Пользователь отправляет сообщение боту в Telegram.

  • Бот принимает сообщение через Telegram Bot API и отправляет запрос к OpenAI API для генерации ответа.

  • Полученный ответ возвращается пользователю через Telegram.

  • Все события и ошибки записываются в лог для мониторинга и отладки.

1. Инициализация бота и API ключей OpenAI

Сначала необходимо настроить API ключи для OpenAI и Telegram.

import openai
import telebot
import logging
import os
import time

openai.api_key = 'Ваш Openai API ключ'
bot = telebot.TeleBot('Ваш Telegram токен')

Здесь мы импортируем необходимые библиотеки и устанавливаем ключи для доступа к API OpenAI и Telegram.

2. Настройка логирования

Логирование позволяет отслеживать события и ошибки в работе бота.

log_dir = os.path.join(os.path.dirname(__file__), 'ChatGPT_Logs')
if not os.path.exists(log_dir):
    os.makedirs(log_dir)
logging.basicConfig(filename=os.path.join(log_dir, 'error.log'), level=logging.ERROR,
                    format='%(levelname)s: %(asctime)s %(message)s', datefmt='%d/%m/%Y %H:%M:%S')

Мы создаем директорию для логов и настраиваем параметры логирования для удобства анализа.

3. Обработка команд и сообщений

Определим функции для обработки команд /start и /bot, а также любых текстовых сообщений.

@bot.message_handler(commands=['start'])
def send_welcome(message):
    bot.reply_to(message, 'Привет!\nЯ ChatGPT 3.5 Telegram Bot\U0001F916\nЗадай мне любой вопрос и я постараюсь на него ответить')

def generate_response(prompt):
    completion = openai.ChatCompletion.create(
        model="gpt-3.5-turbo",
        messages=[{"role": "user", "content": prompt}]
    )
    return completion.choices[0].message.content

@bot.message_handler(commands=['bot'])
def command_message(message):
    prompt = message.text
    response = generate_response(prompt)
    bot.reply_to(message, text=response)

@bot.message_handler(func=lambda _: True)
def handle_message(message):
    prompt = message.text
    response = generate_response(prompt)
    bot.send_message(chat_id=message.from_user.id, text=response)
  • send_welcome: Отправляет приветственное сообщение при запуске бота.

  • generate_response: Генерирует ответ с помощью OpenAI API.

  • command_message и handle_message: Обрабатывают команды и текстовые сообщения, генерируя ответы с помощью OpenAI API.

4. Основной цикл

Запуск основного цикла для обработки сообщений и повторного подключения при сбоях.

print('ChatGPT Bot is working')

while True:
    try:
        bot.polling()
    except (telebot.apihelper.ApiException, ConnectionError) as e:
        logging.error(str(e))
        time.sleep(5)
        continue

Здесь мы запускаем основной цикл, который постоянно проверяет новые сообщения и обрабатывает их. В случае ошибки бот записывает ее в лог и пытается восстановить соединение.

Получаем готовый код для нашего бота

import openai
import telebot
import logging
import os
import time

openai.api_key = 'Openai_api_key'
bot = telebot.TeleBot('Telegram_token')

log_dir = os.path.join(os.path.dirname(__file__), 'ChatGPT_Logs')

if not os.path.exists(log_dir):
    os.makedirs(log_dir)

logging.basicConfig(filename=os.path.join(log_dir, 'error.log'), level=logging.ERROR,
                    format='%(levelname)s: %(asctime)s %(message)s', datefmt='%d/%m/%Y %H:%M:%S')

@bot.message_handler(commands=['start'])
def send_welcome(message):
    bot.reply_to(message, 'Привет!\nЯ ChatGPT 3.5 Telegram Bot\U0001F916\nЗадай мне любой вопрос и я постараюсь на него ответиь')

def generate_response(prompt):
        completion = openai.ChatCompletion.create(
            model="gpt-3.5-turbo",
            messages=[
                {"role": "user", "content": prompt}
            ]
        )
        return completion.choices[0].message.content


@bot.message_handler(commands=['bot'])
def command_message(message):
    prompt = message.text
    response = generate_response(prompt)
    bot.reply_to(message, text=response)


@bot.message_handler(func = lambda _: True)
def handle_message(message):
    prompt = message.text
    response = generate_response(prompt)
    bot.send_message(chat_id=message.from_user.id, text=response)


print('ChatGPT Bot is working')

while True:
    try:
        bot.polling()
    except (telebot.apihelper.ApiException, ConnectionError) as e:
        logging.error(str(e))
        time.sleep(5)
        continue

Развертывание на сервер c доступом к API OpenAI

Для развертывания мы остановимся на платформе Amvera.

Почему выбрали Amvera?

  • Amvera предоставляет встроенное бесплатное проксирование до API OpenAI. Вам не потребуется зарубежная виртуальная машина или VPN.

  • Развертывание идет максимально просто. Через загрузку кода в интерфейсе, либо через git push.

  • Стартовый баланс, который позволит протестировать сервис.

Запускаем нашего бота в облаке

Перейдем теперь к самой интересной части данной статьи, как развернуть бота так, чтобы не использовать иностранные серверы и не настраивать проксирование к API OpenAI.

Регистрация в сервисе

  1. На сайте Amvera нажимаем на кнопку «Регистрация».

  2. Заполняем последовательно все поля.

  3. Подтверждаем, что мы не робот, и тыкаем на большую синюю кнопку «Регистрация»

  4. Остается только подтвердить указанную почту, перейдя по ссылке в письме.

Создание проекта и размещение бота

  1. На появившейся после входа странице нажимаем на кнопку «Создать» или «Создать первый!».

  2. Выбираем тариф. Может показаться, что тарифные планы предоставляют слишком мало ресурса по сравнению с VPS. Однако в VPS часть ресурсов используется операционной системой, а тут весь выделенный ресурс уходит только на развертываемое приложение. Нам хватит тарифа Пробный, но первый запуск лучше осуществить на одном из старших тарифов, чтобы убедиться, что все работает.

    Окно создания нового проекта

    Окно создания нового проекта

  3. Создадим конфигурационный yaml файл. Это можно сделать самостоятельно на основании документации, однако я рекомендую воспользоваться автоматическим графическим инструментом генерации либо сделать это в личном кабинете во вкладке Конфигурация.

    Графический инструмент генерации .yaml файлов

    Графический инструмент генерации .yaml файлов

    1. Мы используем Python, укажем его версию.

    2. requirements.txt — файл с зависимостями. Очень важно указать все используемые в проекте библиотеки в этом файле, чтобы сервис смог их скачать через pip. Необходимо прописать все библиотеки в формате библиотека==версия.

    3. Указываем путь до файла, содержащего точку входа в программу (тот файл, который вы указываете интерпретатору питона, когда запускаете приложение) либо команду запуска.

    4. Если в процессе работы ваш бот использует SQLite, сохраняйте данные в постоянное хранилище /data. В противном случае при перезапуске проекта все данные будут потеряны!

    5. Порт можно указать тот, который используется в коде вашего приложения. Не забудьте изменить локалхост на 0.0.0.0

    6. Нажимаем на кнопку Generate YAML, после чего начинается загрузка файла amvera.yml.

  4. Скачанный файл кладем в корень нашего проекта

  5. Инициируем Git-репозиторий и загружаем наш проект.

    • В корне нашего проекта выполняем команду:  git init (если гит уже инициализирован в вашем проекте, то этого делать не нужно)

    • Привязываем наш локальный гит репозиторий к удаленному репозиторию через команду, которая указана на странице проекта в amvera (имеет формат git remote add amvera >)

      1. Делаем git add . и git commit -m "Initial commit"

      2. Делаем push с нашим проектом, выполняя команду git push amvera master, вводя учетные данные, которые использовались при регистрации в сервисе.

  6. После того как проект запушится в систему, на странице проекта статус поменяется на «Выполняется сборка».

    Успешно развернутый проект

    Успешно развернутый проект

  7. Как только проект соберется, он перейдет в стадию: «Выполняется развертывание», а после в статус «Успешно развернуто».

    Успешно развернутый проект

    Успешно развернутый проект

  8. Если по какой-то причине проект не развернулся, можно обратиться к логам сборки и логам приложения для отладки. Если Проект завис в статусе «Сборка» на долгое время, а логи сборки не отображаются, то стоит ещё раз проверить корректность amvera.yml файла.

Ура, все работает! Теперь наш Telegram-бот развернут и готов к использованию. Вы можете проделать все шаги из статьи и протестировать его, отправив команды и сообщения, чтобы увидеть, как он работает с API OpenAI.

© Habrahabr.ru