{"id":90,"date":"2026-08-29T19:20:45","date_gmt":"2026-08-29T22:20:45","guid":{"rendered":"https:\/\/postping.com.br\/blog\/bot-telegram-wordpress\/"},"modified":"2026-08-29T19:20:45","modified_gmt":"2026-08-29T22:20:45","slug":"bot-telegram-wordpress","status":"publish","type":"post","link":"https:\/\/postping.com.br\/blog\/bot-telegram-wordpress\/","title":{"rendered":"Bot do Telegram no WordPress avisa cada artigo publicado"},"content":{"rendered":"<p>Quatro etapas separam um bot rec\u00e9m-criado de um grupo do Telegram que recebe o aviso a cada artigo publicado no WordPress: criar o bot, descobrir o <code>chat_id<\/code>, mandar a primeira mensagem e prender o disparo ao momento da publica\u00e7\u00e3o. A terceira etapa \u00e9 onde a maioria das tentativas trava, com a mensagem que some sem explica\u00e7\u00e3o, e \u00e9 ali que a resposta da API precisa ser lida inteira.<\/p>\n<h2>Crie o bot no BotFather e trate o token como senha<\/h2>\n<p>O bot nasce dentro do pr\u00f3prio Telegram, em conversa com o <a href=\"https:\/\/t.me\/BotFather\" rel=\"nofollow\">@BotFather<\/a>. O comando \u00e9 <code>\/newbot<\/code>. Ele pede um nome de exibi\u00e7\u00e3o e um nome de usu\u00e1rio, que precisa ser \u00fanico e terminar em <code>bot<\/code>, e devolve o token: uma cadeia parecida com <code>110201543:AAHdqTcvCH1vGWJxfSeofSAs0K5PALDsaw<\/code>, o exemplo que a pr\u00f3pria <a href=\"https:\/\/core.telegram.org\/bots\/features\" rel=\"nofollow\">documenta\u00e7\u00e3o de recursos de bots<\/a> usa. O n\u00famero antes dos dois-pontos identifica o bot; o resto \u00e9 a chave.<\/p>\n<p>A documenta\u00e7\u00e3o de introdu\u00e7\u00e3o \u00e9 direta sobre o peso desse valor: quem tem o token tem controle total sobre o bot. Ele n\u00e3o deve ficar no reposit\u00f3rio do tema, nem colada em um campo de plugin qualquer que grave em texto puro na tabela de op\u00e7\u00f5es. Uma constante no <code>wp-config.php<\/code>, fora do controle de vers\u00e3o, resolve para a maioria dos sites.<\/p>\n<p>Antes de montar qualquer mensagem, confirme que o token responde. Toda chamada \u00e0 Bot API tem a mesma forma, sempre por HTTPS:<\/p>\n<p><code>curl -s \"https:\/\/api.telegram.org\/bot&lt;TOKEN&gt;\/getMe\"<\/code><\/p>\n<p>A resposta boa traz <code>\"ok\": true<\/code> e, dentro de <code>result<\/code>, o <code>id<\/code>, o <code>first_name<\/code> e o <code>username<\/code> do bot. Se vier <code>\"ok\": false<\/code> com <code>error_code<\/code> 401, existem tr\u00eas causas, nesta ordem de frequ\u00eancia. A primeira \u00e9 a palavra <code>bot<\/code> ter ficado de fora da URL: a documenta\u00e7\u00e3o pede explicitamente que o token seja prefixado por ela, e <code>\/110201543:AAHdq...\/getMe<\/code> n\u00e3o \u00e9 um endere\u00e7o v\u00e1lido. A segunda \u00e9 um espa\u00e7o ou uma quebra de linha que veio junto na hora de copiar do aplicativo, o que costuma acontecer quando o token passa por um bloco de anota\u00e7\u00f5es. A terceira \u00e9 algu\u00e9m ter rodado <code>\/token<\/code> no BotFather em algum momento: esse comando gera um token novo e derruba o anterior no mesmo instante, sem aviso para quem estava usando.<\/p>\n<h2>Descubra o chat_id do grupo antes de escrever qualquer c\u00f3digo<\/h2>\n<p>O bot precisa de um <code>chat_id<\/code> para saber o destino, e esse n\u00famero n\u00e3o aparece em lugar nenhum da interface do Telegram. Ele sai de uma mensagem que o bot tenha recebido.<\/p>\n<p>Adicione o bot ao grupo, mande ali uma mensagem qualquer e chame o m\u00e9todo que devolve as atualiza\u00e7\u00f5es pendentes:<\/p>\n<p><code>curl -s \"https:\/\/api.telegram.org\/bot&lt;TOKEN&gt;\/getUpdates\"<\/code><\/p>\n<p>Dentro de <code>result<\/code>, cada item traz <code>message.chat.id<\/code>. Copie o valor exatamente como veio, sinal inclu\u00eddo, e guarde junto o <code>message.chat.type<\/code>, porque o tipo do chat muda o que \u00e9 poss\u00edvel fazer depois:<\/p>\n<ul>\n<li>Em conversa privada, o identificador \u00e9 o da pessoa, e a mensagem s\u00f3 sai se ela j\u00e1 tiver falado com o bot antes.<\/li>\n<li>Em grupo comum, o identificador vale enquanto o grupo for grupo. Se ele for promovido a supergrupo, o Telegram envia uma mensagem de servi\u00e7o com o campo <code>migrate_to_chat_id<\/code>, o identificador novo, e o antigo para de valer.<\/li>\n<li>Em supergrupo e em canal com nome p\u00fablico, d\u00e1 para usar <code>@nomedocanal<\/code> no lugar do n\u00famero: o par\u00e2metro <code>chat_id<\/code> do <code>sendMessage<\/code> aceita o nome de usu\u00e1rio de supergrupo ou canal nesse formato.<\/li>\n<li>Em canal, o bot precisa ser administrador com a permiss\u00e3o de publicar. \u00c9 o campo <code>can_post_messages<\/code>, que a documenta\u00e7\u00e3o descreve como o direito do administrador de publicar mensagens no canal, e que s\u00f3 existe para canais.<\/li>\n<\/ul>\n<p>Quando o <code>getUpdates<\/code> volta com <code>result<\/code> vazio, quase sempre \u00e9 um destes quatro casos. O mais comum \u00e9 o modo de privacidade, ligado por padr\u00e3o em todo bot que n\u00e3o entrou no grupo como administrador: nessa configura\u00e7\u00e3o o bot recebe apenas os comandos endere\u00e7ados a ele, no formato <code>\/comando@nomedobot<\/code>, as respostas \u00e0s mensagens dele, as mensagens de servi\u00e7o e o <code>\/start<\/code> quando ele foi o \u00faltimo bot a falar no grupo. Uma mensagem solta como \u201coi\u201d n\u00e3o chega nele. Mande <code>\/start@nomedobot<\/code> no grupo e a atualiza\u00e7\u00e3o aparece. Para desligar o modo de privacidade de vez existe o <code>\/setprivacy<\/code> no BotFather, com a ressalva que a pr\u00f3pria documenta\u00e7\u00e3o faz: o bot precisa ser removido e adicionado de novo ao grupo para a mudan\u00e7a valer.<\/p>\n<p>Se a mensagem de comando tamb\u00e9m n\u00e3o aparecer, procure um webhook configurado para esse bot. A documenta\u00e7\u00e3o \u00e9 categ\u00f3rica: o <code>getUpdates<\/code> n\u00e3o funciona quando existe um webhook ativo, porque os dois s\u00e3o formas mutuamente exclusivas de receber atualiza\u00e7\u00f5es. Cheque com <code>getWebhookInfo<\/code>, que devolve o campo <code>url<\/code> vazio quando o bot est\u00e1 em long polling, e use <code>deleteWebhook<\/code> para voltar ao m\u00e9todo manual. Sobram dois motivos, ambos ligados ao tempo. As atualiza\u00e7\u00f5es ficam guardadas no servidor por no m\u00e1ximo 24 horas, ent\u00e3o a mensagem que voc\u00ea mandou no grupo ontem j\u00e1 n\u00e3o est\u00e1 mais l\u00e1. E uma chamada anterior com <code>offset<\/code> confirma e descarta tudo o que veio antes daquele ponto, o que costuma acontecer quando duas pessoas depuram o mesmo bot ao mesmo tempo.<\/p>\n<h2>Dispare a primeira mensagem e leia a resposta inteira<\/h2>\n<p>Com token e <code>chat_id<\/code> em m\u00e3os, o envio \u00e9 um POST:<\/p>\n<p><code>curl -s -X POST \"https:\/\/api.telegram.org\/bot&lt;TOKEN&gt;\/sendMessage\" -H \"Content-Type: application\/json\" -d '{\"chat_id\":\"-1001234567890\",\"text\":\"Artigo novo no ar\"}'<\/code><\/p>\n<p>O campo <code>text<\/code> aceita de 1 a 4096 caracteres depois da interpreta\u00e7\u00e3o das entidades. Folgado para um aviso de artigo, apertado para quem decide mandar o excerto inteiro junto: um resumo de 500 palavras passa do limite e a chamada volta com erro.<\/p>\n<p>A parte que mais gente pula \u00e9 ler a resposta. A Bot API sempre devolve um objeto com o campo booleano <code>ok<\/code>; quando ele \u00e9 <code>false<\/code>, vem tamb\u00e9m <code>description<\/code>, em texto leg\u00edvel, e <code>error_code<\/code>. Alguns erros trazem ainda um objeto <code>parameters<\/code> feito justamente para tratamento autom\u00e1tico. \u00c9 a mesma disciplina de leitura de erro que vale para <a href=\"https:\/\/postping.com.br\/blog\/erro-webhook-401-404-429\/\">os c\u00f3digos 401, 404 e 429 de um webhook<\/a>: o n\u00famero diz a categoria, a descri\u00e7\u00e3o diz o caso.<\/p>\n<p>O erro que trava a maior parte dos primeiros testes \u00e9 o <code>Forbidden: bot can't initiate conversation with a user<\/code>. Ele aparece quando algu\u00e9m tenta mandar a primeira mensagem para uma pessoa, e n\u00e3o para um grupo. A regra est\u00e1 na introdu\u00e7\u00e3o aos bots: bots n\u00e3o podem come\u00e7ar conversas com usu\u00e1rios, e o usu\u00e1rio precisa adicionar o bot a um grupo ou mandar uma mensagem para ele antes. N\u00e3o existe contorno. Em uma <a href=\"https:\/\/github.com\/tdlib\/telegram-bot-api\/issues\/198\" rel=\"nofollow\">discuss\u00e3o no reposit\u00f3rio do servidor da Bot API<\/a>, um desenvolvedor descreve o caso preciso: recebeu o evento de pedido de entrada em um grupo, tentou responder \u00e0 pessoa no privado e levou o mesmo 403, porque clicar num link de convite n\u00e3o conta como iniciar conversa. Para avisar uma equipe, isso deixa de ser obst\u00e1culo: o destino \u00e9 um grupo ou um canal, onde a restri\u00e7\u00e3o n\u00e3o se aplica.<\/p>\n<p>Duas outras respostas aparecem cedo. Uma \u00e9 o erro de formata\u00e7\u00e3o: se voc\u00ea mandar <code>parse_mode<\/code> como <code>MarkdownV2<\/code>, todo caractere reservado precisa vir escapado, e t\u00edtulos de artigo costumam ter par\u00eanteses, h\u00edfen e ponto de exclama\u00e7\u00e3o. Mande a primeira mensagem sem <code>parse_mode<\/code> nenhum, confirme que ela chega, e s\u00f3 depois acrescente formata\u00e7\u00e3o. A outra \u00e9 o 429, que vem acompanhado de <code>parameters.retry_after<\/code>, definido na documenta\u00e7\u00e3o como o n\u00famero de segundos que faltam para o pedido poder ser repetido. O FAQ oficial d\u00e1 os limites que provocam isso: cerca de uma mensagem por segundo em um mesmo chat, no m\u00e1ximo 20 mensagens por minuto em um grupo e algo em torno de 30 por segundo em envio em massa. Um blog que publica cinco artigos por dia n\u00e3o encosta nesses n\u00fameros; uma rotina que reprocessa o arquivo inteiro do site encosta na primeira execu\u00e7\u00e3o.<\/p>\n<h2>Ligue o disparo \u00e0 publica\u00e7\u00e3o e confirme que ele continua vivo<\/h2>\n<p>No WordPress, o gancho certo \u00e9 o <code>transition_post_status<\/code>, que dispara quando um post muda de status e recebe o status novo, o status antigo e o objeto do post. A verifica\u00e7\u00e3o obrigat\u00f3ria \u00e9 comparar os dois: o gancho tamb\u00e9m roda quando o post \u00e9 salvo sem mudan\u00e7a de status, e sem essa compara\u00e7\u00e3o a equipe recebe um aviso novo a cada corre\u00e7\u00e3o de v\u00edrgula em um artigo j\u00e1 publicado. Interessa apenas a transi\u00e7\u00e3o em que o status novo \u00e9 <code>publish<\/code> e o antigo n\u00e3o era.<\/p>\n<p>O envio em si \u00e9 um <code>wp_remote_post<\/code>. O tempo limite padr\u00e3o de uma requisi\u00e7\u00e3o HTTP no WordPress \u00e9 de 5 segundos, e ela \u00e9 bloqueante por padr\u00e3o: enquanto o Telegram n\u00e3o responde, o editor fica esperando a tela de publica\u00e7\u00e3o voltar. Passar <code>blocking<\/code> como <code>false<\/code> devolve o controle na hora, mas a documenta\u00e7\u00e3o avisa o que se perde: a chamada n\u00e3o recebe resposta nenhuma do servidor remoto. Voc\u00ea troca cinco segundos de espera pela descri\u00e7\u00e3o do erro. Para um aviso de artigo, o caminho que se sustenta \u00e9 manter a chamada bloqueante com tempo limite curto e gravar o par <code>error_code<\/code> e <code>description<\/code> em log, porque \u00e9 esse texto que responde, tr\u00eas semanas depois, por que o grupo ficou em sil\u00eancio. Quando a l\u00f3gica de fila e de repeti\u00e7\u00e3o come\u00e7a a crescer, releia <a href=\"https:\/\/postping.com.br\/blog\/o-que-e-webhook\/\">o que um webhook faz e o que ele n\u00e3o faz<\/a> antes de seguir montando pe\u00e7a por pe\u00e7a.<\/p>\n<p>Montar isso \u00e0 m\u00e3o d\u00e1 trabalho de uma tarde. A manuten\u00e7\u00e3o \u00e9 que se estende: token trocado, grupo promovido a supergrupo, log que ningu\u00e9m l\u00ea. O Post Ping cobre essa parte com uma mensagem autom\u00e1tica no grupo ou canal a cada artigo publicado, pela Bot API, com o token guardado criptografado no banco do site, e roda uma verifica\u00e7\u00e3o di\u00e1ria dos artigos que ficaram sem notifica\u00e7\u00e3o, que \u00e9 justamente quando a falha passa despercebida. A lista completa do que o plugin faz est\u00e1 em <a href=\"https:\/\/postping.com.br\/recursos\">recursos<\/a>.<\/p>\n<p>Feita a liga\u00e7\u00e3o, publique um post de teste de verdade, com status <code>publish<\/code>, e confira se a mensagem entra no grupo no mesmo minuto. Depois edite esse mesmo post, salve de novo e confirme que nenhuma segunda mensagem chegou: \u00e9 o que prova que a compara\u00e7\u00e3o de status est\u00e1 correta. Faltando isso, provoque a falha de prop\u00f3sito. Rode <code>\/token<\/code> no BotFather para invalidar o token em uso e publique outro post de teste. O aviso est\u00e1 sob controle se o seu log registrar o 401 com a descri\u00e7\u00e3o vinda da API. Se a \u00fanica forma de descobrir a pane for algu\u00e9m da equipe comentar que faz tempo que n\u00e3o v\u00ea nada no grupo, falta o registro do erro, n\u00e3o o bot.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Bot do Telegram no WordPress: como criar o bot, achar o chat_id do grupo e entender por que a primeira mensagem n\u00e3o chega, com 401 e 403 lidos na resposta.<\/p>\n","protected":false},"author":1,"featured_media":89,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[2],"tags":[],"class_list":["post-90","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-webhooks"],"_links":{"self":[{"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/posts\/90","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/comments?post=90"}],"version-history":[{"count":0,"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/posts\/90\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/media\/89"}],"wp:attachment":[{"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/media?parent=90"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/categories?post=90"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/postping.com.br\/blog\/wp-json\/wp\/v2\/tags?post=90"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}