Como fazer um bot para o Telegram em PHP

Como fazer um bot para o Telegram em PHP
Como fazer um bot para o Telegram em PHP

Este é um exemplo básico de como fazer um bot do Telegram em PHP. Bots do Telegram são robôs que se comportam como uma conversa no Telegram, porém respondem a comando definidos pelo programador, neste exemplo configuraremos usaremos um ‘webhook’ para receber as requisições, este bot aplicará as classes de filtros gramáticas, que já postei anteriormente aqui no blog.

Este exemplo criei a partir do exemplo da própria documentação do Telegram. Confira também toda a documentação no site do Telegram.

Solicitando uma chave de acesso ao Telegram

Como todas as requisições serão feitas por uma conexão HTTP, é necessário ter uma chave de acesso privada para o seu bot, para isso, inicie uma conversa com o BotFather e digite /newbot ele irá te perguntar o nome do seu bot e gerar uma chave de acesso no final, guarde ela, usaremos mais adiante.

Criando um bot no BotFather
Criando um bot no BotFather

Projeto

Diferente do exemplo anterior que demonstrei em Java, onde são realizadas várias requisições a todo momento ao servidor do Telegram para conferir se há alguma nova requisição para ser tratada, neste exemplo usaremos o recurso de ‘Webhook’, que basicamente dirá ao Telegram que, para cada nova requisição ao bot, será repassada para um endereço público na web, que será nosso PHP, onde será tratado.

index.php

<!--?php include 'filtro.php'; define('BOT_TOKEN', ''); define('API_URL', 'https://api.telegram.org/bot'.BOT_TOKEN.'/'); define('WEBHOOK_URL', ''); function apiRequestWebhook($method, $parameters) { if (!is_string($method)) { error_log("Method name must be a string\n"); return false; } if (!$parameters) { $parameters = array(); } else if (!is_array($parameters)) { error_log("Parameters must be an array\n"); return false; } $parameters["method"] = $method; header("Content-Type: application/json"); echo json_encode($parameters); return true; } function exec_curl_request($handle) { $response = curl_exec($handle); if ($response === false) { $errno = curl_errno($handle); $error = curl_error($handle); error_log("Curl returned error $errno: $error\n"); curl_close($handle); return false; } $http_code = intval(curl_getinfo($handle, CURLINFO_HTTP_CODE)); curl_close($handle); if ($http_code &gt;= 500) {
    // do not wat to DDOS server if something goes wrong
    sleep(10);
    return false;
  } else if ($http_code != 200) {
    $response = json_decode($response, true);
    error_log("Request has failed with error {$response['error_code']}: {$response['description']}\n");
    if ($http_code == 401) {
      throw new Exception('Invalid access token provided');
    }
    return false;
  } else {
    $response = json_decode($response, true);
    if (isset($response['description'])) {
      error_log("Request was successfull: {$response['description']}\n");
    }
    $response = $response['result'];
  }

  return $response;
}

function apiRequest($method, $parameters) {
  if (!is_string($method)) {
    error_log("Method name must be a string\n");
    return false;
  }

  if (!$parameters) {
    $parameters = array();
  } else if (!is_array($parameters)) {
    error_log("Parameters must be an array\n");
    return false;
  }

  foreach ($parameters as $key =&gt; &amp;$val) {
    // encoding to JSON array parameters, for example reply_markup
    if (!is_numeric($val) &amp;&amp; !is_string($val)) {
      $val = json_encode($val);
    }
  }
  $url = API_URL.$method.'?'.http_build_query($parameters);

  $handle = curl_init($url);
  curl_setopt($handle, CURLOPT_RETURNTRANSFER, true);
  curl_setopt($handle, CURLOPT_CONNECTTIMEOUT, 5);
  curl_setopt($handle, CURLOPT_TIMEOUT, 60);

  return exec_curl_request($handle);
}

function apiRequestJson($method, $parameters) {
  if (!is_string($method)) {
    error_log("Method name must be a string\n");
    return false;
  }

  if (!$parameters) {
    $parameters = array();
  } else if (!is_array($parameters)) {
    error_log("Parameters must be an array\n");
    return false;
  }

  $parameters["method"] = $method;

  $handle = curl_init(API_URL);
  curl_setopt($handle, CURLOPT_RETURNTRANSFER, true);
  curl_setopt($handle, CURLOPT_CONNECTTIMEOUT, 5);
  curl_setopt($handle, CURLOPT_TIMEOUT, 60);
  curl_setopt($handle, CURLOPT_POSTFIELDS, json_encode($parameters));
  curl_setopt($handle, CURLOPT_HTTPHEADER, array("Content-Type: application/json"));

  return exec_curl_request($handle);
}

function processMessage($message) {
  // process incoming message
  $message_id = $message['message_id'];
  $chat_id = $message['chat']['id'];
  if (isset($message['text'])) {
    // incoming text message
    $text = filtro($message['text']);

     apiRequest("sendMessage", array('chat_id' =&gt; $chat_id, "text" =&gt; $text));
  }
}

if (isset($_GET['webhook'])){
	if ($_GET['webhook']=='create'){
		echo 'Criando webhook';
		apiRequest('setWebhook',  array('url' =&gt; WEBHOOK_URL));
	}
	if ($_GET['webhook']=='delete'){
		echo 'Removendo webhook';
		apiRequest('setWebhook',  array('url' =&gt; 'delete'));
	}
	exit;
}

$content = file_get_contents("php://input");
$update = json_decode($content, true);

if (!$update) {
  // receive wrong update, must not happen
  exit;
}

if (isset($update["message"])) {
  processMessage($update["message"]);
}
?-->

Neste exemplo usarei as funções que publiquei a um tempo atrás no blog, que são recursos para corrigir um texto, acerta acentuações, pontuações, letras maiúsculas no inicio das frase, dentre outros, a função pode ser obtida aqui. Crie um arquivo filtro.php com o conteúdo doas funções de filtro, serão importadas em ‘include ‘filtro.php’;’

No define BOT_TOKEN, informe a chave fornecida pelo BotFather.

No define WEBHOOK_URL, informe o caminho do ser arquivo em seu servidor.

DICA 1: Proteja esta URL em seu site, crie um diretório ‘secreto’ em seu servidor, com o valor da chave do bot por exemplo: https://www.paulocollares.com.br/bots/[CHAVE]/index.php

 

DICA 2: A URL do Webhook tem que ser obrigatoriamente uma url segura (https), seu o seu domínio não possui uma conexão segura configurada, você pode tentar usar a do seu servidor, caso for uma conta compartilhada.
No meu caso, por exemplo, meu site está hospedado na Hostgator, se tentar acessar https://www.paulocollares.com.br/ encontrará um erro de configuração, mas o endereço da Hostgator está configurado corretamente, sabendo que posso acessar meu diretório pelo domínio do DNS, configurei meu webhook assim: https://ns136.hostgator.com.br/~[USUARIO]/bots/[CHAVE]/index.php

Suba os arquivos para seu servidor, e acesse a primeira vez para configurar o webhook:

  • Criar: https:// … /bots/[CHAVE]/index.php?webhook=create
  • Remover: Criar: https:// … /bots/[CHAVE]/index.php?webhook=delete

Seu bot já está pronto para receber e tratar as requisições:

Bot em uso
Bot em uso

Você pode conferir este meu exemplo aqui.

Um abraço, e fiquem na Paz.

Paulo Collares

Servo de Jesus Cristo, Analista de Sistemas, com especialidade em Engenharia de Software Saiba mais sobre mim

  • Tio nélio Do Rincão

    Otimo artigo meu amigo
    pretendo fazer igual

    Att,
    Tio Nélio do Rincão ( TI & DBA )

  • Jackson Graff

    sei que esse post tem tempos ja, mas poderia explicar melhor o que seria o webhook e qual o codigo dele?

    • Um webhook é um ouvinte que você configura no seu bot do telegram para que toda vez que uma requisição chegar ele redirecionar para um endereço na web, neste caso, após configurar o webhook no seu bot, toda vez que alguém interagir com ele, o telegram vai chamar a URL que você informou, que tem que ser o código PHP acima que irá tratar essa requisição