Apache Airflow на собеседовании Data Engineer

Готовишься к собесу Data Engineer?
Spark, Airflow, ClickHouse, SQL для DE — вопросы с разборами в Telegram
Тренировать DE в Telegram

Зачем Airflow на собесе DE

Airflow — стандарт оркестрации в большинстве российских IT-компаний. На собесе Data Engineer базовые знания Airflow ожидают по умолчанию: что такое DAG, как ставится зависимость между тасками, что такое идемпотентность.

Глубокие вопросы — для middle+:

  • Как работает scheduler и зачем catchup
  • В чём разница между PythonOperator и BashOperator при запуске одного и того же скрипта
  • Когда использовать sensor, а когда — пуллить из downstream
  • Как проектировать DAG, чтобы он переживал перезапуск с любого таска

DAG, операторы, зависимости

DAG (Directed Acyclic Graph) — направленный ациклический граф тасков. Главные элементы:

  • Operator — что делает таск (PythonOperator, BashOperator, KubernetesPodOperator и т.д.)
  • Task — экземпляр оператора в DAG
  • Dependencies — порядок выполнения, через >> или set_upstream/downstream

Минимальный DAG:

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

with DAG(
  'simple_dag',
  start_date=datetime(2026, 1, 1),
  schedule='@daily',
  catchup=False,
) as dag:

  extract = PythonOperator(task_id='extract', python_callable=extract_fn)
  transform = PythonOperator(task_id='transform', python_callable=transform_fn)
  load = PythonOperator(task_id='load', python_callable=load_fn)

  extract >> transform >> load

Что важно знать на собесе:

  • schedule — cron-выражение или alias (@daily, @hourly)
  • catchup — если True, при первом запуске Airflow догонит все execution dates с start_date
  • max_active_runs — сколько одновременных run-ов разрешено для DAG
  • task_concurrency — сколько одновременных запусков одного таска

Идемпотентность и backfill

Идемпотентность — таск можно перезапустить с теми же параметрами и получить тот же результат. Без идемпотентности backfill не работает.

Пример неидемпотентного таска:

INSERT INTO events_agg (date, count)
VALUES ('2026-05-01', 10000);

При повторном запуске — дубликат. Идемпотентный вариант:

DELETE FROM events_agg WHERE DATE = '{{ ds }}';
INSERT INTO events_agg (DATE, count) ... ;

Или upsert с ON CONFLICT DO UPDATE. Или партиционированная таблица с INSERT OVERWRITE PARTITION.

Backfill — запуск DAG для прошлых execution dates. Используется, когда:

  • Нужно перегенерить данные после фикса бага
  • Догнать дни, когда DAG был выключен
  • Заполнить данные за период до запуска DAG

Команда:

airflow dags backfill -s 2026-01-01 -e 2026-01-31 my_dag

На собесе спросят: «Что произойдёт, если запустить backfill на DAG с неидемпотентными тасками?» Ответ: дубликаты, рассинхронизация, длительный дебаг.

XCom и шаблоны Jinja

XCom — механизм передачи данных между тасками. Ограничение — в дефолтном backend (БД) хранится только маленький JSON, для больших объёмов — кастомный backend.

def push_value(**context):
  context['ti'].xcom_push(key='user_count', value=12345)

def pull_value(**context):
  count = context['ti'].xcom_pull(key='user_count')

Jinja-шаблоны — встроены в большинство операторов. Главные переменные:

  • {{ ds }} — execution date в формате YYYY-MM-DD
  • {{ ds_nodash }} — то же без дефисов (для путей)
  • {{ ts }} — execution timestamp ISO
  • {{ macros.ds_add(ds, -7) }} — дата за 7 дней до execution

Используются в SQL-запросах, путях файлов, аргументах bash:

load = BashOperator(
  task_id='load',
  bash_command='spark-submit /jobs/etl.py --date={{ ds }}',
)
Готовишься к собесу Data Engineer?
Spark, Airflow, ClickHouse, SQL для DE — вопросы с разборами в Telegram
Тренировать DE в Telegram

Sensor-операторы

Sensor — ждёт условия, потом завершается. Используется когда зависимость от внешней системы (файл появился, таблица заполнена).

from airflow.sensors.filesystem import FileSensor

wait_file = FileSensor(
  task_id='wait_for_input',
  filepath='/data/input/{{ ds }}.csv',
  poke_interval=60,
  timeout=3600,
  mode='reschedule',
)

Главный антипаттерн — mode='poke' (по дефолту). Sensor занимает worker slot всё время ожидания. На длинных таймаутах это убивает кластер. Используйте mode='reschedule' — sensor освобождает slot между проверками.

Типичные задачи на собесе

1. Спроектировать DAG для ETL

Условие: «Каждый день забираем данные с API, трансформируем, кладём в DWH». Ответ должен включать:

  • Структуру: extract → transform → load
  • Идемпотентность: как работает повторный запуск
  • Обработку ошибок: retries, on_failure_callback
  • Алерты: SLA или callback в Slack

2. Дебаг сломанного DAG

Дают DAG-код с проблемой. Типичные баги: cyclic dependency, неправильный schedule, неидемпотентный таск, race condition между параллельными ветками.

3. Оптимизация медленного DAG

«У нас DAG из 50 тасков выполняется 4 часа. Как ускорить?» Ответ:

  • Параллелить независимые ветки
  • Группировать мелкие таски в один (TaskGroup)
  • Убрать неоправданные sensor-ы
  • Использовать KubernetesPodOperator для тяжёлых тасков
  • Профилировать конкретный таск

4. Архитектура мониторинга

Какие метрики важны: SLA по DAG, время выполнения каждого таска, количество ошибок, задержка scheduler. Где собирать (StatsD, Prometheus).

Частые ошибки

Бизнес-логика в DAG-файле. DAG-файл парсится scheduler каждые 30 секунд. Если в нём тяжёлый код (например, обращения к БД), это ломает scheduler.

Глобальные переменные в DAG. Между парсингами scheduler состояние не сохраняется. Используйте Airflow Variables или Connections, а не модульные переменные.

Sensor в poke-режиме на длинных таймаутах. Worker slot заблокирован, кластер деградирует.

XCom для больших данных. XCom хранится в БД метаданных. Для больших объёмов используйте S3/HDFS + только путь в XCom.

Не использовать catchup=False. При запуске DAG со start_date в прошлом по умолчанию запустит все пропущенные дни. Если этого не хотите — обязательно catchup=False.

FAQ

Какую версию Airflow учить?

Airflow 2.x. Версия 1.x устарела. На собесе спросят, что нового в 2.x: TaskFlow API, dynamic task mapping, dataset-driven scheduling.

Airflow vs Dagster vs Prefect — что выбрать?

Airflow — стандарт в РФ. Dagster и Prefect — современные альтернативы, иногда встречаются в стартапах. Для собеса — учите Airflow.

Сколько практики Airflow нужно для junior DE?

Один-два домашних проекта с боевым DAG (с sensor, XCom, идемпотентностью). На собесе спросят про реальный опыт.

Это официальная информация?

Нет. Статья основана на публичных источниках и опыте кандидатов.