Автоматизация отчётов на Python — гайд для аналитика

Зачем автоматизировать

Каждый понедельник вы открываете базу, пишете SQL, копируете результат в Excel, форматируете, отправляете в Slack. Тратите 40 минут. Через месяц — 160 минут. Через год — 32 часа. На одном отчёте.

Скрипт на Python делает то же самое за 30 секунд без вашего участия. Один раз написать — дальше работает само.

Что стоит автоматизировать:

  • Еженедельные/ежемесячные отчёты с фиксированной структурой
  • Мониторинг метрик с алертами (DAU упал > 20% — сообщение в Slack)
  • Выгрузки для других команд (маркетинг просит свежий отчёт по когортам)
  • Обновление дашбордов, которые не в BI-инструменте

Что НЕ стоит:

  • Одноразовый ad-hoc анализ
  • Отчёты, которые каждый раз разные по структуре
  • Задачи, где 80% времени — интерпретация, а не подготовка данных

Чтение данных

Первый шаг — получить данные. Три основных источника:

Из CSV/Excel

Самый простой вариант. Если данные выгружаются в файл:

import pandas as pd

df = pd.read_csv("data/sales_2026.csv")
# или
df = pd.read_excel("data/report_template.xlsx", sheet_name="Raw")

Подробнее о read_csv — в отдельном гайде.

Из SQL-базы

Напрямую из PostgreSQL, MySQL, ClickHouse:

import pandas as pd
from sqlalchemy import create_engine

engine = create_engine("postgresql://user:pass@host:5432/db")

query = """
SELECT
    DATE_TRUNC('week', created_at) AS week,
    COUNT(DISTINCT user_id) AS active_users,
    SUM(revenue) AS total_revenue
FROM events
WHERE created_at >= CURRENT_DATE - INTERVAL '90 days'
GROUP BY 1
ORDER BY 1
"""

df = pd.read_sql(query, engine)

Из API

Google Analytics, Яндекс.Метрика, внутренние сервисы:

import requests
import pandas as pd

response = requests.get(
    "https://api.example.com/metrics",
    headers={"Authorization": "Bearer TOKEN"},
    params={"date_from": "2026-01-01", "date_to": "2026-03-31"}
)
data = response.json()
df = pd.DataFrame(data["results"])

Трансформация с pandas

После загрузки данных — подготовка: фильтрация, агрегация, расчёт метрик.

# Добавляем расчётные поля
df["arpu"] = df["total_revenue"] / df["active_users"]
df["wow_change"] = df["active_users"].pct_change() * 100

# Фильтруем последние 12 недель
df_recent = df.tail(12)

# Форматируем для отчёта
df_recent["week"] = df_recent["week"].dt.strftime("%d.%m.%Y")
df_recent["total_revenue"] = df_recent["total_revenue"].round(0).astype(int)
df_recent["arpu"] = df_recent["arpu"].round(2)
df_recent["wow_change"] = df_recent["wow_change"].round(1)

Генерация Excel-отчётов

Pandas + openpyxl позволяют создавать отформатированные Excel-файлы:

from openpyxl.styles import Font, PatternFill, Alignment

output_path = "reports/weekly_report.xlsx"

with pd.ExcelWriter(output_path, engine="openpyxl") as writer:
    df_recent.to_excel(writer, sheet_name="Метрики", index=False)

    # Форматирование
    ws = writer.sheets["Метрики"]
    header_fill = PatternFill(start_color="4472C4", fill_color="4472C4",
                               fill_type="solid")
    header_font = Font(color="FFFFFF", bold=True)

    for cell in ws[1]:
        cell.fill = header_fill
        cell.font = header_font
        cell.alignment = Alignment(horizontal="center")

    # Автоширина колонок
    for col in ws.columns:
        max_len = max(len(str(cell.value or "")) for cell in col)
        ws.column_dimensions[col[0].column_letter].width = max_len + 4

Для PDF-отчётов можно использовать Jupyter Notebook + nbconvert или библиотеки вроде WeasyPrint и FPDF.

Отправка в Slack

import requests

def send_slack_report(webhook_url, file_path, message):
    # Текстовое сообщение
    requests.post(webhook_url, json={"text": message})

    # Файл — через Slack API (не webhook)
    requests.post(
        "https://slack.com/api/files.upload",
        headers={"Authorization": "Bearer xoxb-YOUR-TOKEN"},
        data={"channels": "C0123ANALYTICS", "title": "Weekly Report"},
        files={"file": open(file_path, "rb")}
    )

send_slack_report(
    webhook_url="https://hooks.slack.com/services/XXX/YYY/ZZZ",
    file_path="reports/weekly_report.xlsx",
    message="Еженедельный отчёт готов. Основные метрики за неделю 31.03–06.04."
)

По email — через smtplib + email.mime:

import smtplib
from email.mime.multipart import MIMEMultipart
from email.mime.base import MIMEBase
from email import encoders

msg = MIMEMultipart()
msg["From"] = "analytics@company.com"
msg["To"] = "team@company.com"
msg["Subject"] = "Еженедельный отчёт"

with open("reports/weekly_report.xlsx", "rb") as f:
    part = MIMEBase("application", "octet-stream")
    part.set_payload(f.read())
    encoders.encode_base64(part)
    part.add_header("Content-Disposition", "attachment; filename=weekly_report.xlsx")
    msg.attach(part)

with smtplib.SMTP("smtp.company.com", 587) as server:
    server.starttls()
    server.login("analytics@company.com", "password")
    server.send_message(msg)

Расписание: cron и Airflow

cron (простые задачи)

Для одного скрипта — cron на Linux/Mac:

# Каждый понедельник в 9:00
0 9 * * 1 /usr/bin/python3 /home/analyst/scripts/weekly_report.py >> /var/log/report.log 2>&1

Airflow (сложные пайплайны)

Когда скриптов много и между ними есть зависимости — Airflow:

from airflow import DAG
from airflow.operators.python import PythonOperator
from datetime import datetime

dag = DAG("weekly_report", schedule_interval="0 9 * * 1",
          start_date=datetime(2026, 1, 1))

extract = PythonOperator(task_id="extract", python_callable=load_data, dag=dag)
transform = PythonOperator(task_id="transform", python_callable=transform_data, dag=dag)
send = PythonOperator(task_id="send", python_callable=send_report, dag=dag)

extract >> transform >> send

Полный пример: скрипт от данных до Slack

"""weekly_report.py — еженедельный отчёт по метрикам."""

import pandas as pd
import requests
from sqlalchemy import create_engine
from datetime import datetime
import os

# 1. Загрузка данных
engine = create_engine(os.environ["DATABASE_URL"])
df = pd.read_sql("""
    SELECT DATE_TRUNC('week', created_at)::date AS week,
           COUNT(DISTINCT user_id) AS wau,
           SUM(revenue) AS revenue
    FROM events
    WHERE created_at >= CURRENT_DATE - INTERVAL '12 weeks'
    GROUP BY 1 ORDER BY 1
""", engine)

# 2. Расчёт метрик
df["arpu"] = (df["revenue"] / df["wau"]).round(2)
df["wau_change"] = df["wau"].pct_change().mul(100).round(1)

# 3. Сохранение в Excel
output = f"reports/weekly_{datetime.now():%Y%m%d}.xlsx"
df.to_excel(output, index=False, sheet_name="Metrics")

# 4. Формирование сообщения
last = df.iloc[-1]
msg = (f"Отчёт за неделю {last['week']}\n"
       f"WAU: {last['wau']:,} ({last['wau_change']:+.1f}%)\n"
       f"Revenue: {last['revenue']:,.0f}\n"
       f"ARPU: {last['arpu']}")

# 5. Отправка в Slack
requests.post(os.environ["SLACK_WEBHOOK"], json={"text": msg})
print(f"Отчёт отправлен: {output}")

Советы для production-ready скриптов

  1. Логирование: logging вместо print. Когда скрипт упадёт в 3 часа ночи — логи спасут.
  2. Обработка ошибок: try/except с алертом. Если скрипт сломался — отправьте сообщение об ошибке, а не молчите.
  3. Конфигурация: креды и параметры — в переменных окружения, не в коде.
  4. Идемпотентность: скрипт можно запустить дважды без побочных эффектов.
  5. Версионирование: храните скрипты в Git. Отчёт изменился — вы видите, когда и почему.

Подробнее о сохранении результатов — в гайде по to_csv и matplotlib для визуализации.

Вопросы с собеседований

Как бы вы автоматизировали еженедельный отчёт? — Скрипт на Python: pandas для подготовки данных, openpyxl для Excel, отправка в Slack через webhook. Запуск по cron или Airflow. Логирование и алерты при ошибках.

Какие библиотеки Python используете для работы с отчётами? — pandas — обработка данных, openpyxl — Excel, matplotlib/plotly — графики, sqlalchemy — подключение к БД, requests — API и Slack, smtplib — email. Для сложных пайплайнов — Airflow.

Как обеспечить надёжность автоматического скрипта? — Логирование через logging, обработка ошибок с алертами (Slack/email при падении), идемпотентность (повторный запуск не ломает данные), мониторинг (проверять, что скрипт отработал), тесты на тестовых данных.

Когда не стоит автоматизировать отчёт? — Когда отчёт разовый, когда структура каждый раз разная, когда 90% времени — интерпретация, а не подготовка, или когда задачу проще решить через BI-инструмент с автообновлением.

FAQ

С чего начать автоматизацию отчётов?

С самого простого: возьмите отчёт, который вы делаете вручную каждую неделю. Разбейте на шаги: загрузка данных, трансформация, выгрузка, отправка. Напишите скрипт для каждого шага. Запустите вручную несколько раз, убедитесь, что работает. Потом добавьте cron.

Что лучше — cron или Airflow?

Для одного-двух скриптов — cron. Простой, есть на любом сервере, не требует настройки. Для пяти и более скриптов с зависимостями — Airflow. Он даёт UI для мониторинга, retry при ошибках, управление зависимостями между задачами и логирование из коробки.

Можно ли автоматизировать отчёты без Python?

Да. Google Sheets + Apps Script, SQL-шедулеры в BI-инструментах (Looker, Metabase), no-code платформы (Zapier, Make). Но Python даёт максимальную гибкость: любой источник данных, любой формат вывода, любая логика. Для аналитика это самый универсальный инструмент.


Потренируйте вопросы по Python и аналитике — откройте тренажёр. 1500+ вопросов для собеседования аналитика. Бесплатно.