Как написать бота для Телеграмма на go

После реализации бота на Ruby , мне захотелось сделать ещё одного, но уже на моём любимом языке — Golang.

Когда я только начинал работу, информации о библиотеке go-telegram-bot-api у меня не было. Так что пришлось писать бота практически с нуля. В проекте на Ruby все самое сложное делал гем telegram-bot-ruby . Но в этот раз я захотел сам реализовать бота.

После потраченного вечера на поиск информации об архитектуре телеграм ботов, я занялся написанием самого проекта.

Main():

err := initConfig() if err != nil

Сначала бот инициализирует конфиг (ключи и токены) вызывая функцию initConfig(), которая выглядит следующим образом:

func initConfig() error

Тут я использую библиотеку viper для считывания ключей и токенов из файла config.json

После инициализации конфига бот выполняет проверку переменной err, в которую в случае ошибки будет записан код ошибки (точнее не код, а сама ошибка). Если переменная err равна nil, бот продолжит работу, в противном случае в консоль выведется ошибка и main() закроется.

Мастер-класс «Создание telegram бота на Go»

в языке Golang значение nil означает буквально «ничего»

botUrl := «https://api.telegram.org/bot» + viper.GetString(«token») offSet := 0 for < updates, err := getUpdates(botUrl, offSet) if err != nil < fmt.Println(«Something went wrong: «, err) return >for _, update := range updates < respond(botUrl, update) offSet = update.UpdateId + 1 >fmt.Println(updates) >

После работы с инициализацией конфига, бот записывает в переменную botUrl ссылку, по которой он будет получать сообщения, или же слайс объектов Update. botUrl состоит из токена, полученного ранее из файла config.json и ссылки на api.telegram.org . Идентификатор offset нужен для обработки нескольких сообщений.

Далее идёт главный цикл бота, в котором происходит вообще всё. Для работы с пользователем боту необходимо получить от него сообщение, это реализовано с помощью функции getUpdates():

getUpdates()

func getUpdates(botUrl string, offset int) ([]mods.Update, error) < resp, err := http.Get(botUrl + «/getUpdates?offset=» + strconv.Itoa(offset)) if err != nil < return nil, err >defer resp.Body.Close() body, err := ioutil.ReadAll(resp.Body) if err != nil < return nil, err >var restResponse mods.TelegramResponse err = json.Unmarshal(body, return nil, err >return restResponse.Result, nil >

Построчно расписывать не буду, весь процесс в этой функции можно расписать так:

Бот отправляет запрос GET телеграму, на что получает json файл, который переводит в слайс byte’ов. Слайс байтов записывается в структуру restResponse, которая имеет только одно поле — «Result». Result является слайсом объектов Update. В конце функция вернёт поле «Result», т.е слайс обновлений.

Еще по теме:  Как удалить аккаунт Telegram с телефона

type TelegramResponse struct
type Update struct

Структура Update имеет всего два поля: идентификатор обновления и объект Message:

Пишем TELEGRAM бота на GO

type Message struct

У структуры Message есть поле Chat, которое бот использует только для работы с идентификатором чата. Поле Text отвечает за текст сообщения, а поле Sticker нужно для обработки сообщений, состоящих из стикера.

После получения слайса обновлений, бот проходится по каждому объекту Update функцией respond().

respond()

func respond(botUrl string, update mods.Update) error < msg := strings.ToLower(update.Message.Text) if msg != «» < switch msg < . >>

В этой функции я описал весь функционал бота, сначала записывает в переменную msg сообщение, которое берет из объекта Update и переводит в нижний регистр, после чего идёт проверка на то, что отправил пользователь.

Если на вход пришло сообщение, функция пройдется по нему с помощью оператора switch:

switch msg < case «/check»: mods.Check(botUrl, update) return nil case «/git»: mods.CheckGit(botUrl, update) return nil case «/weather7»: mods.SendDailyWeather(botUrl, update, 7) return nil . >

При каждой команде, вызывается определённая функция, после чего respond() возвращает nil, что означает, что всё прошло без ошибок.

> else < if update.Message.Sticker.File_id != «» < mods.SendRandomSticker(botUrl, update) return nil >mods.SendMsg(botUrl, update, «Пока я воспринимаю только текст и стикеры ‍♂️») return nil >

Если же пользователь отправил не текст, а что-то иное, бот сделает проверку на стикер. Если пользователь отправил стикер, бот тоже отправляет в ответ случайный стикер. В остальных случаях бот уведомит пользователя, что воспринимает только текст и стикеры.

Осталось рассказать о командах, но это я сделаю в следующей статье. В целом, это оказался очень интересный проект, над которым я работаю до сих пор. Мало того, что во время реализации бота я накапливаю опыт работы с API, так ещё и получаю очень полезного помощника, который подскажет погоду, курс криптовалюты, отправит смешную картинку с попугаем или котом, найдёт страну по IP адресу, и даже я не знаю, как его функционал изменится через неделю.

Источник: teletype.in

Пишем простого бота для Telegram на Go. Часть 1

Написание бота для Telegram отличный способ попрактиковаться в изучении Go.

Преимущества создания программ под Telegram-бота состоят в том, что для получения результата не нужно отдельно создавать frontend-часть, достаточно реализовать необходимую логику на backend-части и добавить взаимодействие с ботом.
Итак, начинаем процесс создания нового бота и через несколько часов можно будет насладиться результатом

Шаг 1. Регистрация Telegram бота

После этого будет предложено выбрать имя бота и уникальное имя пользователя для бота. Имя пользователя при этом должно заканчиваться на bot.

В результате, будет создан новый пользователь по указанному имени username и token, который понадобится для работы с API Telegram

Еще по теме:  Как делать блиц опросы в Телеграмме

Процесс создания бота

Шаг 2. Постановка задачи для бота

Существуют 2 основных сценария использования бота — взаимодействие с ботом с помощью приватных сообщений и добавление бота в чат группы.

Какие сообщения при этом будет получать бот для анализа?

Все боты вне зависимости от настроек будут получать следующие сообщения:

  • все сервисные сообщения
  • все сообщения из личных каналов сообщений с пользователем
  • все сообщения из каналов, в которых состоит бот

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

Боты с включенным режимом конфиденциальности получат:

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

Шаг 3. Пишем код на Go

Сначала установим библиотеку для работы с API Telegram

go get github.com/go-telegram-bot-api/telegram-bot-api/v5

Далее перейдем к реализации процесса программирования бота.

Простейший бот представляет собой сервис, в данном случае написанный на языке Go, который использует long-polling запросы для получения информации об обновлении данных.

Для подключения к API Telegram необходимо воспользоваться методом NewBotApi . В качестве параметра необходимо указать ключ API полученный на этапе регистрации бота.

Итак, наш бот почти готов. Осталось вставить ключ API и реализовать логику по формированию ответа пользователю

Учим бот анализировать сообщение и формировать ответ

Возвращаемся к постановки первоначальной задачи. Итак нам нужно анализировать текст сообщения от пользователя и формировать ответ.

При этом возможны сценарии, когда бот формирует ответ в виде публичного ответа пользователю в группе или же отправляет сообщение пользователю в личном сообщении

В случае публичного ответа (см. пример выше) мы должны в качестве в методе NewMessage указать идентификатор канала, из которого мы получили сообщение (берем из поля message.Chat.ID ) и заполнить поле ReplyToMessageID сообщения, указав ID сообщения, на которое нужно ответить (берем из поля Message.MessageID )

Пример ответов бота Anfiska в чате группы

В случае приватного ответа, в качестве идентификатора чата мы должны указать ID пользователя, которому мы собираемся отправить сообщение (берем из поля Message.From.ID ). В этом случае поле ReplyToMessageID сообщения проставлять не нужно.

Код отправки сообщения будет выглядеть так:

Источник: dzen.ru

Пишем телеграм бота на Go и AWS Lambda

Будем писать простой телеграм бот, отвечающий тем же сообщением, что и отправили.

Почему AWS Lambda ?

  1. Удобство деплоя, просто пишешь sls deploy , и lambda уже выгружена
  2. Платишь только за время, когда lambda работает
  3. Не надо настраивать никаких серверов, и беспокоиться о масштабировании

Что понадобится?

  • Установленный go
  • Nodejs и npm для установки serverless
  • AWS аккаунт для деплоя

TLDR

  • Клонируем репозиторий https://github.com/R11baka/echotgbot
  • Устанавливаем в .env файле BOT_TOKEN переменную
  • Компилируем бинарник env GOOS=linux go build -o bin/webhook main.go
  • Выгружаем лямбду с помощью sls deploy
  • Устанавливаем webhook с помощью BOT_TOKEN
Еще по теме:  Где в Телеграмм подписки

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

  • Регистирируем пользователя в AWS aws console и получаем aws_access_key_id, и aws_secret_access_key и прописываем их в .aws/credentials файле

Вот как выглядит мой .aws/credentials

cat ~/.aws/credentials [default] aws_access_key_id = ADEFEFEFFEBDXK3 aws_secret_access_key = Zy6ewfir/zGaT1B2/o9JDWDSssdrla region = us-west-1

Регистрация бота

Для начала, нам надо зарегистировать бота в BotFather. Идем по ссылке, отправляем команду BotFather /newbot , придумываем имя боту, описание. В конце, BotFather вернет нам токен бота.Этот токен понадобится,нам для дальнейшей разработки.

Установка Serverless

Serverless-это framework, облегчающий настройку, деплой AWS Lambda функций. Написан на node, поэтому для его установки понадобится nodejs и npm. Устанавливаем serverless через npm

npm install -g serverless

После установки serverless проверяем, все ли установилось

sls -v Framework Core: 2.35.0 (standalone) Plugin: 4.5.3 SDK: 4.2.2 Components: 3.8.2

Теперь можно приступить к конфигурации serverless. Все настройки для serverless лежат в serverless.yml файле,который мы и создадим со следующим контентом

service: echoBot useDotenv: true configValidationMode: error # если в конфиге,чтото неправильно ,то ошибка frameworkVersion: ‘>=1.28.0 events: — http: path: /webhook method: ANY cors: false

Имлементация логики бота на Go

  1. Устанавливаем библиотеки telebot.v2 и aws-lambda-go

➜ go mod init testBot go: creating new go.mod: module testBot ➜ go get -u gopkg.in/tucnak/telebot.v2 go: gopkg.in/tucnak/telebot.v2 upgrade => v2.3.5 go: github.com/pkg/errors upgrade => v0.9.1 ➜ go get github.com/aws/aws-lambda-go go: github.com/aws/aws-lambda-go upgrade => v1.23.0

2. Создаем файл main.go с контентом

package main import ( «encoding/json» «fmt» «github.com/aws/aws-lambda-go/events» «github.com/aws/aws-lambda-go/lambda» tb «gopkg.in/tucnak/telebot.v2» «os» ) func main() < settings := tb.Settings< Token: os.Getenv(«BOT_TOKEN»), Synchronous: true, Verbose: true, >tgBot, err := tb.NewBot(settings) if err != nil < fmt.Println(err) panic(«can’t create bot») >tgBot.Handle(tb.OnText, func(m *tb.Message) < message := m.Text tgBot.Send(m.Sender, message) >) lambda.Start(func(req events.APIGatewayProxyRequest) (events.APIGatewayProxyResponse, error) < var u tb.Update if err = json.Unmarshal([]byte(req.Body), err == nil < tgBot.ProcessUpdate(u) >return events.APIGatewayProxyResponse, nil >) >

Текущая документация в tucnak/telebot.v2 немного устарела, и если просто написать return вместо return events.APIGatewayProxyResponse, nil , то телеграм будет повторно отправлять сообщения к боту.

Deploy бота

  • Создаем файл .env и вставляем API_TOKEN полученный от BotFather

echo API_TOKEN= > .env
sls print
env GOOS=linux go build -o bin/webhook main.go
serverless deploy -v
При успешной выгрузке, мы получим в конце
Service Information service: echoBot stage: dev region: us-west-1 stack: echoBot-dev resources: 11 api keys: None endpoints: ANY — https://y7p31bwnu1.execute-api.us-west-1.amazonaws.com/dev/webhook functions: webhook: echoBot-dev-webhook layers: None

Интеграция с telegram

Осталось сообщить телеграму, какой эндпоинт дергать при получении сообщения. Делается это командой setWebhook

curl https://api.telegram.org/bot/setWebhook?url=

Проверка что webhook установлен, происходит с помощью getWebhookInfo

➜ ~ curl https://api.telegram.org/bot1324913549:AAE1zYMH6K3hF2TOgUQoIP-E1g4rMIamck/setWebhook?url= https://y7p31bwnu1.execute-api.us-west-1.amazonaws.com/dev/webhook ➜ ~ curl https://api.telegram.org/bot1324913549:AAE1zYMH6K3hF2TOgUQoIP-E1g4rMIamck/getWebhookInfo >

Ошибки

Если что-то пошло не так,идем в CloudWatch и смотрим логи,или же из консоли также можно посмотреть логи

sls logs -f webhook

Источник: temofeev.ru

Рейтинг
( Пока оценок нет )
Загрузка ...