Como enviar notificações por e-mail ou pelo Telegram

Nos dois últimos posts, mostramos algumas tarefas relacionadas a finanças pessoais, que podem ser agendadas para executar periodicamente e/ou que podem ajudar mais ainda se puderem enviar notificações. Por esse motivo iremos apresentar scripts para automatizar a notificação ao usuário tanto por e-mail (Gmail, no nosso exemplo) quanto por mensagem instantânea (Telegram, principalmente pelo fato do recurso que precisamos ser gratuito).

Fonte: https://br.freepik.com/

Mantendo suas chaves seguras

Antes de iniciar o assunto objeto deste artigo, é importante falar como cuidar da segurança de chaves, tokens e senhas nas nossas aplicações. Introduzimos este assunto aqui, porque iremos lidar com dados que precisam ser mantidos em sigilo.
O primeiro passo é instalar o pacote dotenv, uma biblioteca que permite carregar variáveis de ambiente a partir de um arquivo .env.

pip install python-dotenv

Em seguida vamos criar um arquivo denominado .env na raiz do projeto. Esse arquivo irá conter variáveis de ambiente no formato NOME_DA_VARIAVEL=VALOR. Por exemplo:
  
EMAIL_USUARIO=usuario123456@gmail.com
EMAIL_SENHA=abcdefghijkl
TOKEN=abcdefghijklmnopqrstuvwxyz
CHAT_ID=1001943736541

Agora criaremos nossos scripts de notificação, quando voltaremos ao dotenv.

Script para enviar noticação utilizando o Gmail

A fim de fazer essa implementação, siga os seguintes passos:

1) Em primeiro lugar, obtenha uma senha de App seguindo as instruções descritas neste link.

Um requisito para criar uma senha de App é que a verificação em duas etapas esteja ativada na sua conta Google.
Cumprida essa exigência, crie uma senha de App. Talvez seja pedido para fazer login na sua conta Google. Após isso, irá aparecer essa tela:
Tela de criação da senha de App

Digite o nome do App e clique em Criar. Será mostrada a senha de 16 dígitos. Copie esse senha agora, ignorando os espaços. Após fechat a tela, você não terá como visualizar ou editá-la, apenas poderá excluí-la.

2) Em seguida, escreva o script de acordo com nossas instruções.

Crie um arquivo .env com este conteúdo, na mesma pasta onde se encontra o programa que enviará o e-mail:

EMAIL_USUARIO=seu email de usuário do Gmail
EMAIL_SENHA=a senha de App criada, sem os espaços

Nosso script inicia com as seguintes importações e inicializações, considerando que já instalou python-dotenv:

# Pacote que permite interagir com SMTP
import smtplib
# Pacote que permite lidar com variáveis de ambiente
from dotenv import load_dotenv
# Pacote para lidar com funções do Sistema Operacional
import os

# Lê variáveis do arquivo .env e as define em os.environ
load_dotenv()

E a função completa, que inicializa um servidor SMTP, informa que queremos enviar e-mail de forma segura usando o protocolo TLS, faz login utilizando o e-mail de usuário e a senha de App e finalmente envia mensagem e encerra a instância de SMTP:

send_email.py
import smtplib
de ambiente
from dotenv import load_dotenv
import os

load_dotenv()


def enviar_email(assunto, mensagem):
    servidor_smtp = smtplib.SMTP('smtp.gmail.com', 587)
    servidor_smtp.starttls()
    email = os.getenv('EMAIL_USUARIO')
    servidor_smtp.login(email, os.getenv('EMAIL_SENHA'))
    servidor_smtp.sendmail(
      email, email, f'Subject: {assunto}\n\n{mensagem}')
    servidor_smtp.quit()

Neste exemplo, estamos enviando o e-mail para nós mesmos, por isso os dois primeiros parâmetros de sendmail() são iguais: o remetente e o destinatário são o mesmo usuário.

Agora podemos juntar o script para monitorar cotação de moeda do post anterior com este para enviar um e-mail de alerta:

import requests
from send_email import enviar_email

LIMITE_SUPERIOR = 5.3
LIMITE_INFERIOR = 5.0


def monitorar_cotacao():
    API_URL = "https://economia.awesomeapi.com.br/last/USD-BRL"
    resp = requests.get(API_URL)
    data = resp.json()
    cotacao_dolar = float(data["USDBRL"]["bid"])
    return cotacao_dolar


if __name__ == "__main__":
    cotacao_atual = monitorar_cotacao()
    if cotacao_atual > LIMITE_SUPERIOR:
        enviar_email(
            "Alerta de Cotacao",
            f"A cotacao do dolar subiu para {cotacao_atual:.2f} BRL.",
        )
    elif cotacao_atual < LIMITE_INFERIOR:
        enviar_email(
            "Alerta de Cotacao",
            f"A cotacao do dolar caiu para {cotacao_atual:.2f} BRL.",
        )

Script para enviar mensagem pelo Telegram

Para este script, precisamos seguir estes passos:

1) Criar um bot no BotFather e obter o token de API

Inicialmente abra o Telegram e procure o usuário @BotFather. Este usuário ajuda a criar e gerenciar bots Telegram. Se você enviar a mensagem /start, ele mostrará todos os comandos que ele pode responder. Assim, para criar um novo bot envie a mensagem /newbot, e siga as instruções. Logo que concluir a criação ele lhe mostrará o token de acesso. Copie-o e o mantenha seguro, pois vamos precisar dele no nosso script.

Em seguida é necessário obter o seu CHAT_ID. Existem algumas alternativas. Uma delas é localizar o usuário @userinfobot e enviar a mensagem /start. Ele irá responder algumas informações, dentre elas Your ID. Copie esse número. É o seu CHAT_ID.

2) Se já tiver instalado python-dotenv, escreva o scrpit conforme as instruções a seguir:

Crie um arquivo .env ou, se existir um na mesma pasta onde estará este novo script, abra-o e inclua as seguintes linhas:

TELEGRAM_TOKEN=seu token de API
CHAT_ID=seu chat_id

Instale a biblioteca:
  
pip install python-telegram-bot

E escreva o script:
  
send_msg_telegram.py
# asyncio é uma biblioteca padrão do Python para programação assíncrona.
import asyncio
import telegram
from dotenv import load_dotenv
import os

load_dotenv()

# Configurações do bot do Telegram
TOKEN = os.getenv('TELEGRAM_TOKEN')
CHAT_ID = os.getenv('CHAT_ID')


async def enviar_mensagem(texto):
    bot = telegram.Bot(token=TOKEN)
    await bot.send_message(chat_id=CHAT_ID, text=texto)


# Exemplo de uso
mensagem = "Olá! Esta é uma mensagem enviada do Python."
asyncio.run(enviar_mensagem(mensagem))

Ao executar esse script você deve receber uma mensagem do bot com nome de usuário que você criou.

Agora podemos incrementar a automação que monitora concursos do post anterior, usando este script para enviar uma notificação pelo Telegram:

import requests
from bs4 import BeautifulSoup
from send_msg_telegram import enviar_mensagem
import asyncio


def verificar_concursos(palavras_chave=[]):
    url = "https://www.pciconcursos.com.br/"
    headers = {
        "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.3"
    }
    response = requests.get(url, headers=headers)
    page_contents = BeautifulSoup(response.text, "html.parser")

    noticias = page_contents.find("div", id="noticias_capa")
    # Procure por palavras-chaves na página
    exist = any(elemento in noticias.get_text().lower() for elemento in palavras_chave)

    return exist


if __name__ == "__main__":
    if verificar_concursos(
        [
            "desenvolvedor",
            "programador",
            "engenheiro de software",
            "tecnologia da informação",
        ]
    ):
        asyncio.run(
            enviar_mensagem(
                "Novo concurso encontrado! Verifique em https://www.pciconcursos.com.br/"
            )
        )

Script bônus

Vamos agendar esses dois scripts utilizando a biblioteca schedule.

1) Primeiro, instale a biblioteca:

pip install schedule

E assim fica:
  
import schedule
import asyncio
import time
from monitorar_concurso import verificar_concursos
from cotacao_moeda import monitorar_cotacao
from send_msg_telegram import enviar_mensagem


def existe_concurso():
    if verificar_concursos(
        [
            "desenvolvedor",
            "programador",
            "engenheiro de software",
            "tecnologia da informação",
        ]
    ):
        asyncio.run(
            enviar_mensagem(
                "Novo concurso encontrado! Verifique em https://www.pciconcursos.com.br/"
            )
        )


def cotacao_dolar():
    cotacao_atual = monitorar_cotacao()
    if cotacao_atual > 5.3:
        asyncio.run(
            enviar_mensagem(
                f"A cotacao do dolar subiu para {cotacao_atual:.2f} BRL."
            )
        )
    elif cotacao_atual < 5.0:
        asyncio.run(
            enviar_mensagem(
                f"A cotacao do dolar caiu para {cotacao_atual:.2f} BRL."
            )
        )


# Agendar execuções
schedule.every().day.at("17:00").do(existe_concurso)
schedule.every(1).hours.do(cotacao_dolar)

while True:
    schedule.run_pending()
    time.sleep(1)

Agendamos o monitor de concursos para rodar todos os dias às 17:00 e o monitor de cotação para executar de hora em hora.

Conclusão

Certamente que podemos melhorar muito essas automações, mas tome isso como um ponto de partida que você vai incrementando. Por exemplo: as palavras-chaves do monitor de concursos e os limites da cotação de moeda podem ser modificados periodicamente utilizando um arquivo de configuração ou mesmo uma interface de usuário. Usuários avançados podem criar uma API utilizando um framework Python tais como Flask ou FastAPI e assim suas automações ficam rodando sem a necessidade de seu próprio computador estar ligado.

Comentários