Como configurar o Telegram e interagir com as próprias notificações (via Node-Red)

Após alguns pedidos de tutorial, segue aqui como criar um flow no Node-Red que envia uma mensagem pelo Telegram sendo depois possível interagir com as notificações, permitindo executar acções e apagando a mensagem no fim.

Exemplo:
image
Depois de responder:
image

Para esse tutorial estou com a versão 0.94.4 do HA + nodered 4.0.1

Nesse tutorial, vão achar estranho ter usado um switch, mas tive alguns problemas usando vários callback, e depois acaba por fazer sentido em ter só um callback no node-red todo e um switch que vai servir para fazer o que desejamos. Com essa solução acabam-se os problemas de só de vez em quando o telegram funcionar plenamente com o node-red.

A flow de NR:

Código para criarem a flow no vosso NR:

[{"id":"6f1cedd0.abf544","type":"tab","label":"Testes","disabled":false,"info":""},{"id":"15387ac.8cc8485","type":"comment","z":"6f1cedd0.abf544","name":"Notifica Luz S.Estar Porta Ligada a 10 min","info":"","x":500,"y":61,"wires":[]},{"id":"3f97f825.03dd78","type":"telegram sender","z":"6f1cedd0.abf544","name":"","bot":"61d70456.dea91c","x":481.8412551879883,"y":193.28565788269043,"wires":[["4decf2a9.fb3f2c"]]},{"id":"26df9031.11021","type":"function","z":"6f1cedd0.abf544","name":"pergunta no telegram","func":"context.global.keyboard = { pending : true, messageId : msg.payload.messageId };\nmsg.payload = { type: 'message', chatId: xxxxxxxx }\nvar opts = {\n    reply_to_message_id: msg.payload.messageId,\n    reply_markup: JSON.stringify({\n        \"inline_keyboard\": [[\n            {\n                \"text\": \"Sim\",\n                \"callback_data\": \"simluzsestarporta\"\n            },\n            {\n                \"text\": \"Não\",\n                \"callback_data\": \"naoluzsestarporta\"\n            }]\n        ]\n    })\n};\nmsg.payload.content = 'Luz S.Estar Porta\\nEsta ligada há 10 min, queres desliga-la?';\nmsg.payload.options = opts;\nreturn [ msg ];","outputs":1,"noerr":0,"x":249.17459106445312,"y":193.28564453125,"wires":[["3f97f825.03dd78"]]},{"id":"4decf2a9.fb3f2c","type":"function","z":"6f1cedd0.abf544","name":"guardar id para depois eliminar","func":"global.set('luzsestarfora', msg.payload.sentMessageId);\nreturn [ msg ];","outputs":1,"noerr":0,"x":745.1745986938477,"y":193.17454719543457,"wires":[[]]},{"id":"dcf46b6f.b18488","type":"stoptimer","z":"6f1cedd0.abf544","duration":"10","units":"Minute","payloadtype":"num","payloadval":"0","name":"10min","x":318,"y":127,"wires":[["1d3b6919.2a3557"],[]]},{"id":"1d3b6919.2a3557","type":"api-current-state","z":"6f1cedd0.abf544","name":"Ainda Ligada?","server":"353ef983.d49596","version":1,"outputs":2,"halt_if":"on","halt_if_type":"str","halt_if_compare":"is_not","override_topic":false,"entity_id":"light.luz_sestar_fora","state_type":"str","state_location":"payload","override_payload":"msg","entity_location":"data","override_data":"msg","blockInputOverrides":false,"x":484.71429443359375,"y":122.28564453125,"wires":[[],["26df9031.11021"]]},{"id":"f1f9ae60.7ba03","type":"server-state-changed","z":"6f1cedd0.abf544","name":"Luz S.Estar Porta","server":"353ef983.d49596","version":"1","entityidfilter":"light.luz_sestar_fora","entityidfiltertype":"exact","outputinitially":false,"state_type":"str","haltifstate":"on","halt_if_type":"str","halt_if_compare":"is_not","outputs":2,"output_only_on_state_change":true,"x":110.66069030761719,"y":123.5001106262207,"wires":[[],["dcf46b6f.b18488"]]},{"id":"560a9a76.0ad1e4","type":"api-call-service","z":"6f1cedd0.abf544","name":"Desligar luz S.Estar Porta","server":"353ef983.d49596","service_domain":"light","service":"turn_off","data":"{\"entity_id\":\"light.luz_sestar_fora\"}","mergecontext":"","output_location":"payload","output_location_type":"msg","x":560.0000610351562,"y":313.7501335144043,"wires":[["880fd274.ada7b"]]},{"id":"3dc0a756.0aadc8","type":"function","z":"6f1cedd0.abf544","name":"respondeu não","func":"//var te = msg.payload\nmsg.payload = { type: 'message', chatId: xxxxx }\nmsg.payload.content = 'Recusou Desligar a Luz S.Estar Porta'\nreturn msg;\n","outputs":1,"noerr":0,"x":534.0000610351562,"y":361.7501335144043,"wires":[["1b6ce43a.5217ac"]]},{"id":"8fd5f7c8.b02808","type":"function","z":"6f1cedd0.abf544","name":"Para Eliminar","func":"var id = global.get('luzsestarfora');\nglobal.set('luzsestarfora', '');\nmsg.payload.type = 'deleteMessage';\nmsg.payload.content = id;\nreturn msg;","outputs":1,"noerr":0,"x":544.7500648498535,"y":413.75003814697266,"wires":[["1b6ce43a.5217ac"]]},{"id":"880fd274.ada7b","type":"function","z":"6f1cedd0.abf544","name":"Luz Desligada","func":"//var te = msg.payload\nmsg.payload = { type: 'message', chatId: xxxxx }\nmsg.payload.content = 'Luz S.Estar Porta Desligada'\nreturn msg;\n","outputs":1,"noerr":0,"x":803.1112442016602,"y":314.83371925354004,"wires":[["1b6ce43a.5217ac"]]},{"id":"1b6ce43a.5217ac","type":"telegram sender","z":"6f1cedd0.abf544","name":"","bot":"61d70456.dea91c","x":1096.7897338867188,"y":345.3017883300781,"wires":[[]]},{"id":"af574478.b91fb8","type":"switch","z":"6f1cedd0.abf544","name":"Callback telegram","property":"payload.content","propertyType":"msg","rules":[{"t":"eq","v":"simluzsestarporta","vt":"str"},{"t":"eq","v":"naoluzsestarporta","vt":"str"}],"checkall":"false","repair":false,"outputs":2,"x":264.00001525878906,"y":355.75006008148193,"wires":[["8fd5f7c8.b02808","560a9a76.0ad1e4"],["8fd5f7c8.b02808","3dc0a756.0aadc8"]]},{"id":"c99936fb.7bffd8","type":"telegram event","z":"6f1cedd0.abf544","name":"","bot":"61d70456.dea91c","event":"callback_query","autoanswer":true,"x":131.25001525878906,"y":261.25004386901855,"wires":[["af574478.b91fb8"]]},{"id":"61d70456.dea91c","type":"telegram bot","z":"","botname":"nodered59100_bot","usernames":"","chatids":"572905755","baseapiurl":"","updatemode":"polling","pollinterval":"300","usesocks":false,"sockshost":"","socksport":"6667","socksusername":"anonymous","sockspassword":"","bothost":"","localbotport":"8443","publicbotport":"8443","privatekey":"","certificate":"","useselfsignedcertificate":false,"verboselogging":false},{"id":"353ef983.d49596","type":"server","z":"","name":"Home Assistant","legacy":false,"hassio":false,"rejectUnauthorizedCerts":true,"ha_boolean":"y|yes|true|on|home|open","connectionDelay":true}]

A ideia, é mandar a mensagem ao telegram se a luz continuar ligada ao fim de 10 min.

Nesse flow vão ter que editar os dados com o os vossos no node “pergunta no telegram”, “respondeu não” e “Luz Desligada” com o vosso chatid correcto. Não esquecer de alterar também os nodes “calback query” e “Telegram sender”.

Explicando um pouco os nodes:

  • Pergunta no telegram: Aqui vamos definir a string do nosso “callback_data” que vamos recuperar no switch.
  • Guardar id para depois eliminar: Vamos guardar o id da mensagem do telegram que vai servir para depois eliminar essa mesma no node Para Eliminar

Ao receber a resposta do Telegram, temos sempre que depois mandar apagar a pergunta. Daí que independentemente a resposta ser sim ou não, temos o node “para eliminar” que vai fazer isso.

Pronto fazendo isso, vão poder realizar perguntas e eliminar as mesmas e assim não responder várias vezes a mesma sem querer.

Segue agora o que tenho para o callback, para terem uma ideia:

3 Likes

Ótimo tópico! :smiley:
Já à algum tempo que ando a pensar em mudar para o telegram, uso o pushbullet. Parece que vai ser desta :+1:

Editei porque acho que faltava umas pequenas explicações.
Obrigado @j_assuncao por ter corrigido um pouco o tutorial :wink:

1 Like

Bom dia,

Posso alterar o código de maneira a ser recebido em dois telegram´s?

Obrigado

Sim, crias outro Telegram e adicionas outro “telegram sender” ao flow.

1 Like

Objectivo não é enviar para outro Bot, mas sim para outro telegram_ID.
Ou seja, eu e a minha esposa receber no bot da que temos criado para interagir com HA.

Nunca testei mas penso que existe a hipótese de colocar dois chatId ou então criar um grupo com os dois e enviar para o chatId do grupo. Como te disse nunca testei mas não vejo motivo para não funcionar.

1 Like

Viva.
Será que me podem ajudar com este tutorial?
Importei o flow e configurei com os meus dados.
A ideia para a utilização é a mesma, avisar quando uma luz estiver ligada mais de 10 minutos.
No meu caso, utilizo um shelly 1L e por isso, no Entity ID tenho switch.luz_alpendre.
Consigo receber as mensagem no telegram que a luz se encontra acesa o problema está na interação. Caso opte por desligar a luz através da mensagem não tenho qualquer reposta na luz.
O que poderei estar a fazer errado?

Anexo algumas imagens para perceberem.

4

Coloca um debug node depois do callback e vê se tens alguma resposta lá.

image

E tira a ligação da saida de cima do callback para o function “Para Eliminar”, é a saída do node “Desligar Luz Alpendre” que deve ligar ao function “Para Eliminar”.

1 Like

Continua a não reagir.
No debug, não me aparece nada.
É assim a ligação?

Tás a mandar essa mensagem para um grupo, certo?
Experimenta enviar apenas para um utilizador do telegram a ver o resultado.

Tens o node callback bem configurado (mesmo bot)?

Se não aparece nada no debug é porque não sai nada do Telegram ou o callback query está mal configurado.

Sim, estou a mandar para um grupo. É o mesmo bot.

Tenho assim:

Experimenta en vez de enviar para um grupo, enviar apenas para um user.
Já li sobre a opção de grupos. Mas nunca usei.
Para um user apenas tem que funcionar.

Eu acabei por criar um grupo porque não tinha conseguido fazer com que enviasse para mim.
Vou tentar procucar como é que se faz.
Obrigado @lopitos e @j_assuncao !

1 Like

Para enviares para ti basta saberes o teu chatID.
Em vez de colocar o chatID do grupo colocas o teu.

@lopitos acabei por criar um novo bot e já consegui, através do @chatid_echo_bot saber o meu chatid.
Agora não envia mensagem nenhuma. Dá erro no telegram sender. :unamused:

Aparece sff no https://discord.gg/Mh9mTEA.
É mais simples

Já descobri o porquê do erro quando estás a usar o grupo. Partilhei a solução no discord, mas é melhor atualizar aqui também.

Quando estás a enviar uma query para um grupo (Chat ID começa por -XXXX), temos que alterar a função que manda a ordem de eliminar a mensagem (questão). Node do exemplo “Para Eliminar”

O Original é:

var id = global.get('portaogaragem');
global.set('portaogaragem', '');
msg.payload.type = 'deleteMessage'; //linha a substituir conforme abaixo
msg.payload.content = id;
return msg;

Em vez deste devemos usar o seguinte:

var id = global.get('luzsesgaragem');
global.set('luzsesgaragem', '');
msg.payload = { type: 'deleteMessage', chatId: -O_TEU_GROUP_CHAT_ID }
//msg.payload.type = 'deleteMessage'; 
msg.payload.content = id;
return msg;

Espero que isto resolva a tua questão.

3 Likes

Copyright © 2017-2021. Todos os direitos reservados
CPHA.pt - info@cpha.pt


FAQ | Termos de Serviço/Regras | Política de Privacidade