Automação

Como automatizar relatórios em Excel com Python

Para automatizar um relatório em Excel com Python, use o pandas para ler e resumir os dados (CSV, outra planilha ou banco), grave o resultado com pd.ExcelWriter e formate com o openpyxl. Depois agende o script no Agendador de Tarefas do Windows ou no cron do Linux, para o arquivo ficar pronto antes de alguém chegar ao escritório.

Atualizado em · Por Luis Henrique Cuba

Quando vale trocar o relatório manual por um script

O candidato clássico é o relatório semanal que alguém monta toda segunda-feira: exporta o CSV do sistema, cola numa planilha, faz tabela dinâmica, pinta o cabeçalho e manda por e-mail. Se os passos são sempre os mesmos, o Python faz tudo em segundos.

O que não vale automatizar é o relatório que muda de formato a cada mês por pedido da diretoria. Primeiro estabilize o modelo; depois escreva o script.

Preparação

  1. 01

    Instale o Python

    Baixe em python.org. No Windows, marque a opção de adicionar o Python ao PATH durante a instalação.

  2. 02

    Crie uma pasta e um ambiente virtual

    Um ambiente por projeto evita que a atualização de um pacote quebre outro script.

    python -m venv .venv
  3. 03

    Ative o ambiente e instale os pacotes

    No Windows: .venv\Scripts\activate. No Linux ou macOS: source .venv/bin/activate.

    pip install pandas openpyxl
  4. 04

    Organize as pastas

    Uma pasta dados para a origem (por exemplo, vendas.csv exportado do ERP) e uma pasta saida para os relatórios gerados.

Script completo: resumo semanal de vendas

from datetime import date, timedelta
from pathlib import Path

import pandas as pd
from openpyxl import load_workbook
from openpyxl.styles import Font, PatternFill

PASTA = Path(__file__).resolve().parent
ORIGEM = PASTA / "dados" / "vendas.csv"
COLUNAS = {"data", "vendedor", "regiao", "valor"}

# 1. Ler e conferir a origem (CSV brasileiro: ; e vírgula decimal)
df = pd.read_csv(ORIGEM, sep=";", decimal=",", encoding="utf-8")
faltando = COLUNAS - set(df.columns)
if faltando:
    raise SystemExit(f"Colunas ausentes no arquivo de origem: {faltando}")
df["data"] = pd.to_datetime(df["data"], dayfirst=True)

# 2. Filtrar a semana anterior (segunda a domingo)
hoje = date.today()
inicio = hoje - timedelta(days=hoje.weekday() + 7)
fim = inicio + timedelta(days=6)
semana = df[(df["data"].dt.date >= inicio) & (df["data"].dt.date <= fim)]

# 3. Resumir por região e vendedor
resumo = (
    semana.groupby(["regiao", "vendedor"], as_index=False)["valor"]
    .sum()
    .sort_values("valor", ascending=False)
)

# 4. Gravar as duas abas com pandas
saida = PASTA / "saida" / f"vendas_{inicio:%Y-%m-%d}.xlsx"
saida.parent.mkdir(exist_ok=True)
with pd.ExcelWriter(saida, engine="openpyxl") as writer:
    resumo.to_excel(writer, sheet_name="Resumo", index=False)
    semana.to_excel(writer, sheet_name="Detalhe", index=False)

# 5. Formatar com openpyxl
wb = load_workbook(saida)
for ws in wb.worksheets:
    for celula in ws[1]:
        celula.font = Font(bold=True, color="FFFFFF")
        celula.fill = PatternFill("solid", start_color="1F4E78")
    ws.freeze_panes = "A2"
    ws.auto_filter.ref = ws.dimensions
    for coluna in ws.columns:
        largura = max(len(str(c.value or "")) for c in coluna) + 2
        ws.column_dimensions[coluna[0].column_letter].width = min(largura, 40)
        if coluna[0].value == "valor":
            for c in coluna[1:]:
                c.number_format = '"R$" #,##0.00'
        if coluna[0].value == "data":
            for c in coluna[1:]:
                c.number_format = "DD/MM/YYYY"
wb.save(saida)
print(f"Relatório gerado: {saida} ({len(semana)} vendas)")
Salve como gerar_relatorio.py na pasta do projeto. Testado com pandas 3.0 e openpyxl 3.1; ajuste os nomes de coluna aos do seu sistema.

Por que pandas e openpyxl juntos

  1. pandas

    Lê CSV, Excel e bancos de dados, filtra, agrupa e cruza tabelas. É onde fica a lógica do relatório.

  2. openpyxl

    Mexe no arquivo .xlsx em si: fontes, cores, largura de coluna, formato de moeda e data, congelar painéis, filtros. O pandas usa o openpyxl por baixo para gravar.

  3. A conferência das colunas

    O passo 1 do script para tudo com uma mensagem clara se o sistema de origem mudar o nome de uma coluna. É a falha mais comum desse tipo de rotina, e é melhor ela aparecer como erro do que como relatório com dados errados.

O que costuma dar errado

  • O sistema de origem exporta o CSV com outro separador ou codificação (por exemplo, latin-1 em vez de utf-8). Teste com um arquivo real antes de agendar.
  • Valores chegam como texto, com R$ e ponto de milhar. Limpe a coluna antes de somar, senão o pandas concatena em vez de somar.
  • O arquivo de saída está aberto no Excel de alguém na hora em que o script roda, e o Windows bloqueia a gravação. Gerar um nome por data, como no exemplo, evita isso.
  • A pasta de rede não está montada quando a tarefa roda de madrugada. Prefira caminhos locais ou confira o acesso no log.
  • Ninguém percebe que o relatório parou. Faça o script avisar por e-mail quando falhar, ou confira o log na primeira semana de cada mudança.

Agendar no Windows e no Linux

  1. 01

    Windows: crie um .bat

    Um arquivo rodar.bat na pasta do projeto chama o Python do ambiente virtual. Assim o agendador não depende do PATH.

    cd /d C:\relatorios
    .venv\Scripts\python.exe gerar_relatorio.py >> log.txt 2>&1
  2. 02

    Windows: agende toda segunda às 7h

    No Prompt de Comando, ou pela interface do Agendador de Tarefas (Criar Tarefa Básica).

    schtasks /create /tn "Relatorio de vendas" /tr C:\relatorios\rodar.bat /sc weekly /d MON /st 07:00
  3. 03

    Linux: edite o crontab

    Rode crontab -e e adicione a linha abaixo (segunda-feira, 7h). Use caminhos absolutos, porque o cron não carrega o seu ambiente.

    0 7 * * 1 cd /opt/relatorios && .venv/bin/python gerar_relatorio.py >> log.txt 2>&1
  4. 04

    Confira o log

    Os dois exemplos gravam a saída e os erros em log.txt. Na primeira semana, abra o log todo dia.

Perguntas frequentes

Como automatizar relatórios em Excel com Python: dúvidas comuns

Dá para enviar o relatório por e-mail automaticamente?

Dá, com a biblioteca smtplib do próprio Python e a classe EmailMessage para anexar o arquivo. Guarde usuário e senha do e-mail em variáveis de ambiente, nunca no código.

O openpyxl abre arquivos .xls antigos?

Não. O openpyxl trabalha com .xlsx e formatos relacionados. Para .xls antigo, salve como .xlsx no Excel ou leia com o pandas usando outro mecanismo de leitura.

Posso atualizar uma planilha existente sem apagar as fórmulas?

Pode, carregando o arquivo com load_workbook e escrevendo só nas células de dados. Evite regravar a planilha inteira com o pandas, que cria o arquivo de novo e perde a formatação e as fórmulas.

Python ou Power Query?

O Power Query resolve bem a transformação dentro do próprio Excel, sem programar. O Python é melhor quando o relatório precisa rodar sozinho em horário fixo, juntar fontes variadas ou ser enviado por e-mail.

Preciso ter o Excel instalado para rodar o script?

Não. O pandas e o openpyxl leem e gravam o arquivo .xlsx diretamente, então o script roda até num servidor Linux sem Office.

Precisa de ajuda para resolver isso na sua empresa?

Respondemos em até 24 horas com as próximas perguntas e uma proposta objetiva.