Písanie telegramového robota v R (časť 3): Ako pridať podporu klávesnice do robota

Toto je tretí článok zo série „Písanie telegramového robota v R“. V predchádzajúcich publikáciách sme sa naučili, ako vytvoriť telegramového robota, posielať cez neho správy, pridávať príkazy a filtre správ do robota. Preto skôr, ako začnete čítať tento článok, vrelo odporúčam prečítať si ho predchádzajúce, pretože Tu sa už nebudem zdržiavať skôr popísanými základmi stavby botov.

V tomto článku zlepšíme použiteľnosť nášho robota pridaním klávesnice, vďaka ktorej bude rozhranie robota intuitívne a ľahko použiteľné.

Písanie telegramového robota v R (časť 3): Ako pridať podporu klávesnice do robota

Všetky články zo série „Písanie telegramového robota v R“

  1. Vytvárame robota a používame ho na odosielanie správ v telegrame
  2. Pridajte do robota podporu príkazov a filtre správ
  3. Ako pridať podporu klávesnice do robota

Obsah

Ak máte záujem o analýzu údajov, mohla by vás zaujímať moja telegram и youtube kanálov. Väčšina obsahu je venovaná jazyku R.

  1. Aké typy klávesníc podporuje telegramový robot?
  2. Klávesnica odpovede
  3. Inline klávesnica
    3.1. Príklad jednoduchého bota s podporou tlačidiel InLine
    3.2. Príklad robota, ktorý hlási aktuálne počasie pre vybrané mesto
    3.3. Príklad robota, ktorý zobrazuje zoznam najnovších článkov s odkazmi na zadaný Hub z habr.com
  4. Záver

Aké typy klávesníc podporuje telegramový robot?

V čase tohto písania telegram.bot umožňuje vytvoriť dva typy klávesníc:

  • Odpoveď – hlavná, bežná klávesnica, ktorá sa nachádza pod panelom na zadávanie textu správy. Takáto klávesnica jednoducho pošle textovú správu robotovi a ako text odošle text, ktorý je napísaný na samotnom tlačidle.
  • Inline – klávesnica spojená s konkrétnou správou robota. Táto klávesnica odosiela údaje robota spojené so stlačeným tlačidlom; tieto údaje sa môžu líšiť od textu napísaného na samotnom tlačidle. A takéto tlačidlá sú spracované cez CallbackQueryHandler.

Aby bot otvoril klávesnicu, je to potrebné pri odosielaní správy prostredníctvom metódy sendMessage(), odovzdajte predtým vytvorenú klávesnicu ako argument reply_markup.

Nižšie sa pozrieme na niekoľko príkladov.

Klávesnica odpovede

Ako som písal vyššie, toto je hlavná klávesnica na ovládanie botov.

Príklad vytvorenia Reply klávesnice z oficiálneho pomocníka

bot <- Bot(token = "TOKEN")
chat_id <- "CHAT_ID"

# Create Custom Keyboard
text <- "Aren't those custom keyboards cool?"
RKM <- ReplyKeyboardMarkup(
  keyboard = list(
    list(KeyboardButton("Yes, they certainly are!")),
    list(KeyboardButton("I'm not quite sure")),
    list(KeyboardButton("No..."))
  ),
  resize_keyboard = FALSE,
  one_time_keyboard = TRUE
)

# Send Custom Keyboard
bot$sendMessage(chat_id, text, reply_markup = RKM)

Vyššie uvedené je príklad z oficiálnej pomoci balíka telegram.bot. Ak chcete vytvoriť klávesnicu, použite funkciu ReplyKeyboardMarkup(), ktorý zase preberá zoznam zoznamov tlačidiel, ktoré sú vytvorené funkciou KeyboardButton().

Prečo v ReplyKeyboardMarkup() Potrebujete odovzdať nielen zoznam, ale aj zoznam zoznamov? Faktom je, že miniete hlavný zoznam a v ňom definujete každý riadok tlačidiel v samostatných zoznamoch, pretože Do jedného radu môžete umiestniť niekoľko tlačidiel.

argument resize_keyboard umožňuje automaticky vybrať optimálnu veľkosť tlačidiel klávesnice a argument one_time_keyboard umožňuje skryť klávesnicu po každom stlačení tlačidla.

Napíšme jednoduchého robota, ktorý bude mať 3 tlačidlá:

  • ID chatu - Vyžiadajte ID rozhovoru pre dialóg s robotom
  • Moje meno - Vyžiadajte si svoje meno
  • Moje prihlásenie - Vyžiadajte si svoje používateľské meno v telegrame

Kód 1: Jednoduchý robot s klávesnicou Reply

library(telegram.bot)

# создаём экземпляр класса Updater
updater <- Updater('ТОКЕН ВАШЕГО БОТА')

# создаём методы
## метод для запуска клавиатуры
start <- function(bot, update) {

  # создаём клавиатуру
  RKM <- ReplyKeyboardMarkup(
    keyboard = list(
      list(KeyboardButton("Чат ID")),
      list(KeyboardButton("Моё имя")),
      list(KeyboardButton("Мой логин"))
    ),
    resize_keyboard = FALSE,
    one_time_keyboard = TRUE
  )

  # отправляем клавиатуру
  bot$sendMessage(update$message$chat_id,
                  text = 'Выберите команду', 
                  reply_markup = RKM)

}

## метод возвразающий id чата
chat_id <- function(bot, update) {

  bot$sendMessage(update$message$chat_id, 
                  text = paste0("Чат id этого диалога: ", update$message$chat_id),
                  parse_mode = "Markdown")

}

## метод возвращающий имя
my_name <- function(bot, update) {

  bot$sendMessage(update$message$chat_id, 
                  text = paste0("Вас зовут ", update$message$from$first_name),
                  parse_mode = "Markdown")

}

## метод возвращающий логин
my_username <- function(bot, update) {

  bot$sendMessage(update$message$chat_id, 
                  text = paste0("Ваш логин ", update$message$from$username),
                  parse_mode = "Markdown")

}

# создаём фильтры
## сообщения с текстом Чат ID
MessageFilters$chat_id <- BaseFilter(function(message) {

  # проверяем текст сообщения
  message$text == "Чат ID"

}
)

## сообщения с текстом Моё имя
MessageFilters$name <- BaseFilter(function(message) {

  # проверяем текст сообщения
  message$text == "Моё имя"

}
)

## сообщения с текстом Мой логин
MessageFilters$username <- BaseFilter(function(message) {

  # проверяем текст сообщения
  message$text == "Мой логин"
)

# создаём обработчики
h_start    <- CommandHandler('start', start)
h_chat_id  <- MessageHandler(chat_id, filters = MessageFilters$chat_id)
h_name     <- MessageHandler(my_name, filters = MessageFilters$name)
h_username <- MessageHandler(my_username, filters = MessageFilters$username)

# добавляем обработчики в диспетчер
updater <- updater + 
            h_start +
            h_chat_id +
            h_name +
            h_username

# запускаем бота 
updater$start_polling()

Spustite vyššie uvedený príklad kódu po nahradení 'Your BOT TOKEN' skutočným tokenom, ktorý ste dostali pri vytváraní robota cez Obaja Otec (Hovoril som o vytvorení robota v prvý článok).

Po spustení dajte robotovi príkaz /start, pretože To je presne to, čo sme definovali na spustenie klávesnice.

Písanie telegramového robota v R (časť 3): Ako pridať podporu klávesnice do robota

Ak je pre vás v súčasnosti ťažké analyzovať daný príklad kódu s vytvorením metód, filtrov a obslužných programov, mali by ste sa vrátiť k predchádzajúcemu článok, v ktorej som to všetko podrobne opísal.

Vytvorili sme 4 metódy:

  • štart — Spustenie klávesnice
  • chat_id — Vyžiadať ID chatu
  • my_name — Vyžiadajte si svoje meno
  • my_username — Vyžiadajte si prihlásenie

Namietať MessageFilters pridali 3 filtre správ na základe ich textu:

  • chat_id — správy s textom "Чат ID"
  • meno — Správy s textom "Моё имя"
  • užívateľské meno — správy s textom "Мой логин"

A vytvorili sme 4 handlery, ktoré na základe daných príkazov a filtrov budú vykonávať zadané metódy.

# создаём обработчики
h_start    <- CommandHandler('start', start)
h_chat_id  <- MessageHandler(chat_id, filters = MessageFilters$chat_id)
h_name     <- MessageHandler(my_name, filters = MessageFilters$name)
h_username <- MessageHandler(my_username, filters = MessageFilters$username)

Samotná klávesnica je vytvorená vo vnútri metódy start() tímom ReplyKeyboardMarkup().

RKM <- ReplyKeyboardMarkup(
    keyboard = list(
      list(KeyboardButton("Чат ID")),
      list(KeyboardButton("Моё имя")),
      list(KeyboardButton("Мой логин"))
    ),
    resize_keyboard = FALSE,
    one_time_keyboard = TRUE
)

V našom prípade sme všetky tlačidlá umiestnili pod seba, ale môžeme ich usporiadať do jedného radu vykonaním zmien v zozname zoznamov tlačidiel. Pretože jeden riadok vnútri klávesnice je vytvorený prostredníctvom vnoreného zoznamu tlačidiel, potom, aby sme mohli zobraziť naše tlačidlá v jednom riadku, musíme prepísať časť kódu na zostavenie klávesnice takto:

RKM <- ReplyKeyboardMarkup(
    keyboard = list(
      list(
          KeyboardButton("Чат ID"),
          KeyboardButton("Моё имя"),
          KeyboardButton("Мой логин")
     )
    ),
    resize_keyboard = FALSE,
    one_time_keyboard = TRUE
)

Písanie telegramového robota v R (časť 3): Ako pridať podporu klávesnice do robota

Klávesnica sa odošle do chatu pomocou metódy sendMessage(), v argumente reply_markup.

  bot$sendMessage(update$message$chat_id,
                  text = 'Выберите команду', 
                  reply_markup = RKM)

Inline klávesnica

Ako som písal vyššie, Inline klávesnica je viazaná na konkrétnu správu. Práca s ňou je o niečo náročnejšia ako s hlavnou klávesnicou.

Spočiatku musíte do robota pridať metódu na volanie vloženej klávesnice.

Ak chcete reagovať na kliknutie na tlačidlo Inline, môžete použiť aj metódu robota answerCallbackQuery(), ktorý môže používateľovi, ktorý stlačí tlačidlo Inline, zobraziť upozornenie v rozhraní telegramu.

Údaje odoslané z tlačidla Inline nie sú textové, takže na ich spracovanie je potrebné vytvoriť špeciálny handler pomocou príkazu CallbackQueryHandler().

Kód na zostavenie klávesnice Inline, ktorý je uvedený v oficiálnej pomoci balíka telegram.bot.

Kód na zostavenie klávesnice Inline z oficiálnej pomoci

# Initialize bot
bot <- Bot(token = "TOKEN")
chat_id <- "CHAT_ID"

# Create Inline Keyboard
text <- "Could you type their phone number, please?"
IKM <- InlineKeyboardMarkup(
  inline_keyboard = list(
    list(
      InlineKeyboardButton(1),
      InlineKeyboardButton(2),
      InlineKeyboardButton(3)
    ),
    list(
      InlineKeyboardButton(4),
      InlineKeyboardButton(5),
      InlineKeyboardButton(6)
    ),
    list(
      InlineKeyboardButton(7),
      InlineKeyboardButton(8),
      InlineKeyboardButton(9)
    ),
    list(
      InlineKeyboardButton("*"),
      InlineKeyboardButton(0),
      InlineKeyboardButton("#")
    )
  )
)

# Send Inline Keyboard
bot$sendMessage(chat_id, text, reply_markup = IKM)

Pomocou príkazu musíte zostaviť vloženú klávesnicu InlineKeyboardMarkup(), na rovnakom princípe ako klávesnica Reply. IN InlineKeyboardMarkup() je potrebné odovzdať zoznam zoznamov Inline tlačidiel, pričom každé jednotlivé tlačidlo je vytvorené funkciou InlineKeyboardButton().

Vložené tlačidlo môže buď odovzdať niektoré údaje robotovi pomocou argumentu callback_dataalebo otvorte akúkoľvek stránku HTML určenú pomocou argumentu url.

Výsledkom bude zoznam, v ktorom je každý prvok zároveň zoznamom tlačidiel Inline, ktoré je potrebné spojiť do jedného riadku.

Ďalej sa pozrieme na niekoľko príkladov robotov s tlačidlami Inline.

Príklad jednoduchého bota s podporou tlačidiel InLine

Najprv napíšeme robota na expresné testovanie na COVID-19. Podľa príkazu /test, pošle vám klávesnicu s dvoma tlačidlami, v závislosti od stlačeného tlačidla vám pošle správu s výsledkami vášho testovania.

Kód 2: Najjednoduchší robot s vloženou klávesnicou

library(telegram.bot)

# создаём экземпляр класса Updater
updater <- Updater('ТОКЕН ВАШЕГО БОТА')

# метод для отправки InLine клавиатуры
test <- function(bot, update) {

  # создаём InLine клавиатуру
  IKM <- InlineKeyboardMarkup(
    inline_keyboard = list(
      list(
        InlineKeyboardButton("Да", callback_data = 'yes'),
        InlineKeyboardButton("Нет", callback_data = 'no')
      )
    )
  )

  # Отправляем клавиатуру в чат
  bot$sendMessage(update$message$chat_id, 
                  text = "Вы болете коронавирусом?", 
                  reply_markup = IKM)
}

# метод для обработки нажатия кнопки
answer_cb <- function(bot, update) {

  # полученные данные с кнопки
  data <- update$callback_query$data

  # получаем имя пользователя, нажавшего кнопку
  uname <- update$effective_user()$first_name

  # обработка результата
  if ( data == 'no' ) {

    msg <- paste0(uname, ", поздравляю, ваш тест на covid-19 отрицательный.")

  } else {

    msg <- paste0(uname, ", к сожалени ваш тест на covid-19 положительный.")

  }

  # Отправка сообщения
  bot$sendMessage(chat_id = update$from_chat_id(),
                  text = msg)

  # сообщаем боту, что запрос с кнопки принят
  bot$answerCallbackQuery(callback_query_id = update$callback_query$id) 
}

# создаём обработчики
inline_h      <- CommandHandler('test', test)
query_handler <- CallbackQueryHandler(answer_cb)

# добавляем обработчики в диспетчер
updater <- updater + inline_h + query_handler

# запускаем бота
updater$start_polling()

Spustite vyššie uvedený príklad kódu po nahradení 'Your BOT TOKEN' skutočným tokenom, ktorý ste dostali pri vytváraní robota cez Obaja Otec (Hovoril som o vytvorení robota v prvý článok).

Výsledok:
Písanie telegramového robota v R (časť 3): Ako pridať podporu klávesnice do robota

Vytvorili sme dve metódy:

  • test — Na odoslanie do chatu Inline klávesnica
  • answer_cb — Na spracovanie údajov odoslaných z klávesnice.

Údaje, ktoré sa budú odosielať z každého tlačidla, sú špecifikované v argumente callback_data, pri vytváraní tlačidla. Údaje odoslané z tlačidla môžete prijímať pomocou konštruktu update$callback_query$data, vo vnútri metódy answer_cb.

Aby robot reagoval na vloženú klávesnicu, metóda answer_cb spracované špeciálnym manipulátorom: CallbackQueryHandler(answer_cb). Ktorý spustí zadanú metódu po kliknutí na tlačidlo Inline. Handler CallbackQueryHandler má dva argumenty:

  • callback — Metóda, ktorú treba spustiť
  • pattern — Filtrujte podľa údajov, ktoré sú viazané na tlačidlo pomocou argumentu callback_data.

V súlade s tým pomocou argumentu pattern Na stlačenie každého tlačidla môžeme napísať samostatnú metódu:

Kód 3: Samostatné metódy pre každé tlačidlo Inline

library(telegram.bot)

# создаём экземпляр класса Updater
updater <- Updater('ТОКЕН ВАШЕГО БОТА')

# метод для отправки InLine клавиатуры
test <- function(bot, update) {  

  # создаём InLine клавиатуру
  IKM <- InlineKeyboardMarkup(
    inline_keyboard = list(
      list(
        InlineKeyboardButton("Да", callback_data = 'yes'),
        InlineKeyboardButton("Нет", callback_data = 'no')
      )
    )
  )

  # Отправляем клавиатуру в чат
  bot$sendMessage(update$message$chat_id, 
                  text = "Вы болете коронавирусом?", 
                  reply_markup = IKM)
}

# метод для обработки нажатия кнопки Да
answer_cb_yes <- function(bot, update) {

  # получаем имя пользователя, нажавшего кнопку
  uname <- update$effective_user()$first_name

  # обработка результата
  msg <- paste0(uname, ", к сожалени ваш текст на covid-19 положительный.")

  # Отправка сообщения
  bot$sendMessage(chat_id = update$from_chat_id(),
                  text = msg)

  # сообщаем боту, что запрос с кнопки принят
  bot$answerCallbackQuery(callback_query_id = update$callback_query$id) 
}

# метод для обработки нажатия кнопки Нет
answer_cb_no <- function(bot, update) {

  # получаем имя пользователя, нажавшего кнопку
  uname <- update$effective_user()$first_name

  msg <- paste0(uname, ", поздравляю, ваш текст на covid-19 отрицательный.")

  # Отправка сообщения
  bot$sendMessage(chat_id = update$from_chat_id(),
                  text = msg)

  # сообщаем боту, что запрос с кнопки принят
  bot$answerCallbackQuery(callback_query_id = update$callback_query$id) 
}

# создаём обработчики
inline_h          <- CommandHandler('test', test)
query_handler_yes <- CallbackQueryHandler(answer_cb_yes, pattern = 'yes')
query_handler_no  <- CallbackQueryHandler(answer_cb_no, pattern = 'no')

# добавляем обработчики в диспетчер
updater <- updater + 
            inline_h + 
            query_handler_yes +
            query_handler_no

# запускаем бота
updater$start_polling()

Spustite vyššie uvedený príklad kódu po nahradení 'Your BOT TOKEN' skutočným tokenom, ktorý ste dostali pri vytváraní robota cez Obaja Otec (Hovoril som o vytvorení robota v prvý článok).

Teraz sme napísali 2 samostatné metódy t.j. jeden spôsob, pre každé stlačenie tlačidla a použitý argument pattern, pri vytváraní ich handlerov:

query_handler_yes <- CallbackQueryHandler(answer_cb_yes, pattern = 'yes')
query_handler_no  <- CallbackQueryHandler(answer_cb_no, pattern = 'no')

Kód metódy končí answer_cb tímom bot$answerCallbackQuery(callback_query_id = update$callback_query$id), ktorý robotovi oznámi, že boli prijaté údaje z vloženej klávesnice.

Príklad robota, ktorý hlási aktuálne počasie pre vybrané mesto

Skúsme napísať robota, ktorý požaduje údaje o počasí.

Logika jeho práce bude nasledovná. Spočiatku tým /start voláte na hlavnú klávesnicu, ktorá má iba jedno tlačidlo „Počasie“. Kliknutím na toto tlačidlo dostanete pomocou klávesnice Inline správu na výber mesta, pre ktoré chcete zistiť aktuálne počasie. Vyberte jedno z miest a získajte aktuálne počasie.

V tomto príklade kódu použijeme niekoľko dodatočných balíkov:

  • httr — balík na prácu s požiadavkami HTTP, na základe ktorého je postavená práca s ľubovoľným API. V našom prípade použijeme bezplatné API openweathermap.org.
  • stringr — balík na prácu s textom, v našom prípade ho použijeme na vygenerovanie správy o počasí vo vybranom meste.

Kód 4: Robot, ktorý hlási aktuálne počasie pre vybrané mesto

library(telegram.bot)
library(httr)
library(stringr)

# создаём экземпляр класса Updater
updater <- Updater('ТОКЕН ВАШЕГО БОТА')

# создаём методы
## метод для запуска основной клавиатуры
start <- function(bot, update) {

  # создаём клавиатуру
  RKM <- ReplyKeyboardMarkup(
    keyboard = list(
      list(
        KeyboardButton("Погода")
      )
    ),
    resize_keyboard = TRUE,
    one_time_keyboard = TRUE
  )

  # отправляем клавиатуру
  bot$sendMessage(update$message$chat_id,
                  text = 'Выберите команду', 
                  reply_markup = RKM)

}

## Метод вызова Inine клавиатуры
weather <- function(bot, update) {

  IKM <- InlineKeyboardMarkup(
    inline_keyboard = list(
      list(
        InlineKeyboardButton(text = 'Москва', callback_data = 'New York,us'),
        InlineKeyboardButton(text = 'Санкт-Петербург', callback_data = 'Saint Petersburg'),
        InlineKeyboardButton(text = 'Нью-Йорк', callback_data = 'New York')
      ),
      list(
        InlineKeyboardButton(text = 'Екатеринбург', callback_data = 'Yekaterinburg,ru'),
        InlineKeyboardButton(text = 'Берлин', callback_data = 'Berlin,de'),
        InlineKeyboardButton(text = 'Париж', callback_data = 'Paris,fr')
      ),
      list(
        InlineKeyboardButton(text = 'Рим', callback_data = 'Rome,it'),
        InlineKeyboardButton(text = 'Одесса', callback_data = 'Odessa,ua'),
        InlineKeyboardButton(text = 'Киев', callback_data = 'Kyiv,fr')
      ),
      list(
        InlineKeyboardButton(text = 'Токио', callback_data = 'Tokyo'),
        InlineKeyboardButton(text = 'Амстердам', callback_data = 'Amsterdam,nl'),
        InlineKeyboardButton(text = 'Вашингтон', callback_data = 'Washington,us')
      )
    )
  )

  # Send Inline Keyboard
  bot$sendMessage(chat_id = update$message$chat_id, 
                  text = "Выберите город", 
                  reply_markup = IKM)
}

# метод для сообщения погоды
answer_cb <- function(bot, update) {

  # получаем из сообщения город
  city <- update$callback_query$data

  # отправляем запрос
  ans <- GET('https://api.openweathermap.org/data/2.5/weather', 
             query = list(q     = city,
                          lang  = 'ru',
                          units = 'metric',
                          appid = '4776568ccea136ffe4cda9f1969af340')) 

  # парсим ответ
  result <- content(ans)

  # формируем сообщение
  msg <- str_glue("{result$name} погода:n",
                  "Текущая температура: {result$main$temp}n",
                  "Скорость ветра: {result$wind$speed}n",
                  "Описание: {result$weather[[1]]$description}")

  # отправляем информацию о погоде
  bot$sendMessage(chat_id = update$from_chat_id(),
                  text    = msg)

  bot$answerCallbackQuery(callback_query_id = update$callback_query$id) 
}

# создаём фильтры
## сообщения с текстом Погода
MessageFilters$weather <- BaseFilter(function(message) {

  # проверяем текст сообщения
  message$text == "Погода"

}
)

# создаём обработчики
h_start         <- CommandHandler('start', start)
h_weather       <- MessageHandler(weather, filters = MessageFilters$weather)
h_query_handler <- CallbackQueryHandler(answer_cb)

# добавляем обработчики в диспетчер
updater <- updater + 
              h_start +
              h_weather +
              h_query_handler

# запускаем бота
updater$start_polling()

Spustite vyššie uvedený príklad kódu po nahradení 'Your BOT TOKEN' skutočným tokenom, ktorý ste dostali pri vytváraní robota cez Obaja Otec (Hovoril som o vytvorení robota v prvý článok).

V dôsledku toho bude náš robot fungovať takto:
Písanie telegramového robota v R (časť 3): Ako pridať podporu klávesnice do robota

Schematicky môže byť tento robot znázornený takto:
Písanie telegramového robota v R (časť 3): Ako pridať podporu klávesnice do robota

V našom meteorologickom robote sme vytvorili 3 dostupné metódy:

  • Začať — Spustite hlavnú klávesnicu robota
  • počasie — Spustite inline klávesnicu a vyberte mesto
  • answer_cb — Hlavná metóda, ktorá si vyžiada počasie z API pre dané mesto a pošle ho do chatu.

metóda Začať spustíme ho príkazom /start, ktorú realizuje handler CommandHandler('start', start).

Ak chcete spustiť metódu počasie vytvorili sme filter s rovnakým názvom:

# создаём фильтры
## сообщения с текстом Погода
MessageFilters$weather <- BaseFilter(function(message) {

  # проверяем текст сообщения
  message$text == "Погода"

}
)

A túto metódu voláme s nasledujúcou obsluhou správ: MessageHandler(weather, filters = MessageFilters$weather).

A na záver naša hlavná metóda answer_cb reaguje na stlačenie tlačidiel Inline, čo je implementované špeciálnym handlerom: CallbackQueryHandler(answer_cb).

Vo vnútri metódy answer_cb, načítame dáta odoslané z klávesnice a zapíšeme ich do premennej city: city <- update$callback_query$data. Potom si vyžiadame údaje o počasí z API, vygenerujeme a odošleme správu a nakoniec použijeme metódu answerCallbackQuery s cieľom informovať robota, že sme spracovali kliknutie na tlačidlo Inline.

Príklad robota, ktorý zobrazuje zoznam najnovších článkov s odkazmi na zadaný Hub z hab.com.

Predstavujem tohto robota, aby som vám ukázal, ako zobraziť tlačidlá Inline, ktoré vedú na webové stránky.

Logika tohto robota je podobná predchádzajúcej, najprv spustíme hlavnú klávesnicu pomocou príkazu /start. Potom nám robot poskytne zoznam 6 centier, z ktorých si môžeme vybrať, vyberieme centrum, ktoré nás zaujíma, a dostaneme 5 najnovších publikácií z vybraného centra.

Ako ste pochopili, v tomto prípade musíme získať zoznam článkov a na tento účel použijeme špeciálny balík habR, ktorá vám umožňuje vyžiadať si články od Habra a niektoré štatistiky o nich v R.

Nainštalujte balík habR možné iba z githubu, ku ktorému budete potrebovať ďalší balík devtools. Na inštaláciu použite nižšie uvedený kód.

install.packages('devtools')
devtools::install_github('selesnow/habR')

Teraz sa pozrime na kód na zostavenie robota opísaného vyššie:

Kód 5: Robot, ktorý zobrazuje zoznam najnovších článkov vo vybranom centre

library(telegram.bot)
library(habR)

# создаём экземпляр класса Updater
updater <- Updater('ТОКЕН ВАШЕГО БОТА')

# создаём методы
## метод для запуска основной клавиатуры
start <- function(bot, update) {

  # создаём клавиатуру
  RKM <- ReplyKeyboardMarkup(
    keyboard = list(
      list(
        KeyboardButton("Список статей")
      )
    ),
    resize_keyboard = TRUE,
    one_time_keyboard = TRUE
  )

  # отправляем клавиатуру
  bot$sendMessage(update$message$chat_id,
                  text = 'Выберите команду', 
                  reply_markup = RKM)

}

## Метод вызова Inine клавиатуры
habs <- function(bot, update) {

  IKM <- InlineKeyboardMarkup(
    inline_keyboard = list(
      list(
        InlineKeyboardButton(text = 'R', callback_data = 'R'),
        InlineKeyboardButton(text = 'Data Mining', callback_data = 'data_mining'),
        InlineKeyboardButton(text = 'Data Engineering', callback_data = 'data_engineering')
      ),
      list(
        InlineKeyboardButton(text = 'Big Data', callback_data = 'bigdata'),
        InlineKeyboardButton(text = 'Python', callback_data = 'python'),
        InlineKeyboardButton(text = 'Визуализация данных', callback_data = 'data_visualization')
      )
    )
  )

  # Send Inline Keyboard
  bot$sendMessage(chat_id = update$message$chat_id, 
                  text = "Выберите Хаб", 
                  reply_markup = IKM)
}

# метод для сообщения погоды
answer_cb <- function(bot, update) {

  # получаем из сообщения город
  hub <- update$callback_query$data

  # сообщение о том, что данные по кнопке получены
  bot$answerCallbackQuery(callback_query_id = update$callback_query$id, 
                          text = 'Подождите несколько минут, запрос обрабатывается') 

  # сообщение о том, что надо подождать пока бот получит данные
  mid <- bot$sendMessage(chat_id = update$from_chat_id(),
                         text    = "Подождите несколько минут пока, я соберу данные по выбранному Хабу")

  # парсим Хабр
  posts <- head(habr_hub_posts(hub, 1), 5)

  # удаляем сообщение о том, что надо подождать
  bot$deleteMessage(update$from_chat_id(), mid$message_id) 

  # формируем список кнопок
  keys <- lapply(1:5, function(x) list(InlineKeyboardButton(posts$title[x], url = posts$link[x])))

  # формируем клавиатуру
  IKM <- InlineKeyboardMarkup(
    inline_keyboard =  keys 
    )

  # отправляем информацию о погоде
  bot$sendMessage(chat_id = update$from_chat_id(),
                  text    = paste0("5 наиболее свежих статей из Хаба ", hub),
                  reply_markup = IKM)

}

# создаём фильтры
## сообщения с текстом Погода
MessageFilters$hubs <- BaseFilter(function(message) {

  # проверяем текст сообщения
  message$text == "Список статей"

}
)

# создаём обработчики
h_start         <- CommandHandler('start', start)
h_hubs          <- MessageHandler(habs, filters = MessageFilters$hubs)
h_query_handler <- CallbackQueryHandler(answer_cb)

# добавляем обработчики в диспетчер
updater <- updater + 
  h_start +
  h_hubs  +
  h_query_handler

# запускаем бота
updater$start_polling()

Spustite vyššie uvedený príklad kódu po nahradení 'Your BOT TOKEN' skutočným tokenom, ktorý ste dostali pri vytváraní robota cez Obaja Otec (Hovoril som o vytvorení robota v prvý článok).

V dôsledku toho dostaneme tento výsledok:
Písanie telegramového robota v R (časť 3): Ako pridať podporu klávesnice do robota

Napevno sme zakódovali zoznam Hubov dostupných na výber v metóde habs:

## Метод вызова Inine клавиатуры
habs <- function(bot, update) {

  IKM <- InlineKeyboardMarkup(
    inline_keyboard = list(
      list(
        InlineKeyboardButton(text = 'R', callback_data = 'r'),
        InlineKeyboardButton(text = 'Data Mining', callback_data = 'data_mining'),
        InlineKeyboardButton(text = 'Data Engineering', callback_data = 'data_engineering')
      ),
      list(
        InlineKeyboardButton(text = 'Big Data', callback_data = 'bigdata'),
        InlineKeyboardButton(text = 'Python', callback_data = 'python'),
        InlineKeyboardButton(text = 'Визуализация данных', callback_data = 'data_visualization')
      )
    )
  )

  # Send Inline Keyboard
  bot$sendMessage(chat_id = update$message$chat_id, 
                  text = "Выберите Хаб", 
                  reply_markup = IKM)
}

Príkazom dostaneme zoznam článkov zo zadaného Hubu habr_hub_posts(), z balíka habR. Zároveň upozorňujeme, že nepotrebujeme zoznam článkov na celý čas, ale iba prvú stranu, na ktorej sa nachádza 20 článkov. Z výslednej tabuľky pomocou príkazu head() Necháme len 5 najlepších, čo sú najnovšie články.

  # парсим Хабр
  posts <- head(habr_hub_posts(hub, 1), 5)

Logika je veľmi podobná predchádzajúcemu robotovi, ale v tomto prípade generujeme Inline klávesnicu so zoznamom článkov dynamicky pomocou funkcie lapply().

  # формируем список кнопок
  keys <- lapply(1:5, function(x) list(InlineKeyboardButton(posts$title[x], url = posts$link[x])))

  # формируем клавиатуру
  IKM <- InlineKeyboardMarkup(
    inline_keyboard =  keys 
    )

Do textu tlačidla vložíme názov článku posts$title[x], a v argumentácii url odkaz na článok: url = posts$link[x].

Ďalej vytvoríme filter, obslužné programy a spustíme nášho robota.

Záver

Teraz bude používanie robotov, ktoré napíšete, oveľa pohodlnejšie, pretože sa budú ovládať z klávesnice a nie zadávaním príkazov. Minimálne pri interakcii s botom cez smartfón klávesnica výrazne zjednoduší proces jej používania.

V ďalšom článku prídeme na to, ako vybudovať logický dialóg s botom a pracovať s databázami.

Zdroj: hab.com

Pridať komentár