$ sudo teach IT
Модуль 1 · Введение

Что такое Ruff и зачем он нужен

Ruff — один инструмент вместо пяти. Линтер, форматировщик и замена целого зоопарка Python-утилит.

📖 Теория 🕐 ~15 минут
⚡

Что такое Ruff

Ruff — это линтер и форматировщик для Python, написанный на Rust. Он проверяет код на соответствие стандартам, находит ошибки и форматирует файлы — и всё это в 10–100 раз быстрее, чем аналогичные Python-инструменты.

Ruff реализует правила из более чем 50 популярных плагинов и линтеров в одном бинарнике без единой внешней зависимости. Это означает, что вам больше не нужно устанавливать flake8, black, isort, pyupgrade, autoflake и десятки плагинов по отдельности — один pip install ruff заменяет всё.

Будучи написанным на Rust, Ruff компилируется в нативный машинный код, который работает без интерпретатора и сборщика мусора. Это даёт ему колоссальное преимущество в скорости перед инструментами, написанными на Python. Помимо скорости, Ruff предлагает первоклассную интеграцию с редакторами кода через Language Server Protocol (LSP), встроенное кеширование для повторных запусков, параллельную обработку файлов и полную совместимость с конфигурацией через pyproject.toml.

💡 Ruff используется в FastAPI, Pandas, Pydantic, Airflow, SciPy, Hugging Face и тысячах других популярных проектов.

Ruff — это проект компании Astral, основанной Чарли Маршем. Та же компания создала uv — сверхбыстрый менеджер пакетов для Python, который также написан на Rust. Экосистема Astral стремится переосмыслить инструментарий Python-разработчика, делая его быстрее, надёжнее и удобнее.

Первая стабильная версия Ruff (0.0.0) была выпущена в августе 2022 года, и уже к концу 2023 года проект насчитывал более 15 000 звёзд на GitHub и использовался тысячами организаций по всему миру. К 2025 году Ruff стал стандартом де-факто для линтинга и форматирования Python-кода, заменив legacy-инструменты в большинстве современных проектов.

🔄

Что Ruff заменяет

Ruff — это не просто ещё один инструмент. Это консолидация целой экосистемы в один бинарник. Вот список того, что Ruff заменяет «из коробки»:

flake8 → Линтинг стиля кода (PEP 8), неиспользуемые импорты, логические ошибки
black → Автоматическое форматирование кода
isort → Сортировка и группировка импортов
pyupgrade → Обновление синтаксиса до современного Python
autoflake → Автоматическое удаление неиспользуемого кода
bandit → Проверка на уязвимости безопасности
pydocstyle → Проверка docstring-ов
50+ плагинов → flake8-bugbear, pep8-naming, flake8-docstrings и другие

Каждый из перечисленных инструментов требует отдельной установки, отдельной конфигурации и отдельного запуска. Ruff объединяет их в одной команде. Вот наглядное сравнение: чтобы покрыть ту же функциональность без Ruff, вам потребуется установить 5–10 разных пакетов, согласовать их конфигурации (а они часто конфликтуют!), и запускать их последовательно — что занимает в десятки раз больше времени.

Полный список правил и их источников

На момент написания курса Ruff поддерживает более 900 встроенных правил, разделённых на категории. Каждая категория соответствует определённому плагину или источнику:

Префикс Источник Описание
E/WpycodestyleОшибки и предупреждения стиля PEP 8
FPyflakesЛогические ошибки: неиспользуемые импорты, неопределённые переменные
IisortПорядок и группировка импортов
Npep8-namingИменование: CamelCase, snake_case, UPPER_CASE
UPpyupgradeСовременный синтаксис Python
Bflake8-bugbearРаспространённые баги
Sflake8-banditПроверка безопасности
SIMflake8-simplifyУпрощение кода
DpydocstyleСтиль документации
RUFRuff-specificУникальные правила Ruff
🚀

Почему Ruff такой быстрый

Скорость Ruff — не маркетинговая уловка, а результат архитектурных решений. Давайте разберём их подробно.

1. Написан на Rust

Rust — компилируемый язык системного программирования без сборщика мусора и без накладных расходов на интерпретацию. Ruff компилируется в один бинарник (ELF/PE/Mach-O), который запускается напрямую процессором. Для сравнения: flake8 написан на Python и при каждом запуске интерпретатор Python загружает и парсит исходный код flake8, его зависимости и плагины — это занимает больше времени, чем сам анализ!

2. Параллельная обработка

Ruff использует многопоточность для параллельной проверки файлов. В то время как flake8 обрабатывает файлы последовательно (один за другим), Ruff распределяет файлы по нескольким потокам, используя все доступные ядра процессора. На 8-ядерной машине Ruff может проверять 8 файлов одновременно.

3. Кеширование

Ruff сохраняет результаты анализа в кеше. При повторном запуске он проверяет, изменился ли файл (по времени модификации и содержимому). Если файл не изменился — Ruff пропускает его и использует закешированный результат. На практике второй и последующие запуски Ruff на том же проекте выполняются за миллисекунды.

4. Один процесс вместо пяти

Без Ruff типичный пайплайн «проверка кода» выглядит так: запустить flake8 (3 секунды), запустить black --check (2 секунды), запустить isort --check (1 секунда), запустить pyupgrade (0.5 секунды), запустить bandit (2 секунды). Итого ~8.5 секунд. И каждый инструмент загружает свой интерпретатор Python. Ruff делает всё это в одном процессе за доли секунды.

5. Эффективные структуры данных

Ruff использует AST (Abstract Syntax Tree) и трюки с zero-copy парсингом. Вместо того чтобы строить несколько разных представлений кода для разных правил, Ruff строит одно и прогоняет все правила по нему. Современные алгоритмы обхода дерева и кеширование поддеревьев дают дополнительный прирост.

⚡ Реальные бенчмарки: на проекте CPython (1.5 млн строк кода) Ruff завершает полный линтинг за ~0.5 секунды. flake8 на том же проекте — за 30–60 секунд. Ruff в 60–100 раз быстрее.

Вот как выглядят бенчмарки на CPython (данные с официального репозитория Ruff):

Инструмент Время Относительно Ruff
Ruff~0.5 с1x
flake8~30 с~60x медленнее
Black~10 с~20x медленнее
pylint~120 с~240x медленнее
🎯

Для кого этот курс

Этот курс подойдёт:

  • Начинающим Python-разработчикам — вы узнаете современные best practices по поддержке чистоты кода с самого начала.
  • Опытным разработчикам — которые устали от медленных flake8 и black и хотят перейти на Ruff.
  • DevOps-инженерам — которые настраивают CI/CD и хотят добавить молниеносную проверку кода в пайплайны.
  • Тимлидам — которые ищут единый стандарт форматирования и линтинга для команды.
  • Мейнтейнерам open-source проектов — Ruff используется тысячами проектов, и знание его настройки критически важно.

Что вы узнаете на курсе

  • Устанавливать и запускать Ruff
  • Настраивать линтинг через select/ignore
  • Форматировать код через ruff format
  • Интегрировать Ruff в pre-commit, CI/CD и редакторы
  • Мигрировать с flake8, black, isort на Ruff
  • Настраивать Ruff для больших проектов и монорепозиториев
🌳

Экосистема Astral

Ruff — часть экосистемы инструментов от Astral. Помимо Ruff, компания разрабатывает:

  • uv — менеджер пакетов и проектов для Python, написанный на Rust. Замена pip, pip-tools, virtualenv, poetry. В 10–100 раз быстрее pip.
  • ty — инструмент для работы с типами, следующий шаг эволюции mypy и pyright.

Эти инструменты объединяет общая философия: Rust, скорость, нулевая конфигурация «из коробки» и отличная совместимость с существующей экосистемой Python.

📊

Ruff в цифрах

900+
встроенных правил
50+
плагинов заменяет
100x
быстрее flake8
0 с
внешних зависимостей
🏢

Кто уже использует Ruff

Ruff принят в самых крупных и требовательных проектах Python-экосистемы:

  • Apache Airflow — платформа для оркестрации рабочих процессов
  • Apache Superset — BI-платформа для визуализации данных
  • FastAPI — современный веб-фреймворк
  • Pandas — библиотека для анализа данных
  • SciPy — научные вычисления
  • Hugging Face Transformers — NLP-библиотека
  • Dagster — платформа для data orchestration
  • Zulip — open-source чат для команд
  • Bokeh — визуализация данных
  • Delta Lake — storage layer для озёр данных

И тысячи других проектов. Ruff — это не экспериментальный инструмент, а проверенное решение, используемое в production буквально миллионами разработчиков.

🏗️

Архитектура Ruff

Чтобы понять, почему Ruff настолько быстр, полезно разобраться в его внутренней архитектуре. В отличие от большинства Python-инструментов, которые построены как набор плагинов, загружаемых во время выполнения, Ruff использует совершенно иной подход.

Единый AST вместо цепочки плагинов

Flake8 работает по принципу загрузки плагинов: каждый плагин — это отдельный Python-модуль, который импортируется, инициализируется и запускается. Каждый плагин строит свой собственный AST (Abstract Syntax Tree) или обходит уже построенный. При 20 плагинах это 20 инициализаций и 20 обходов дерева. Ruff же строит AST один раз и прогоняет по нему все правила в одном проходе. Это даёт выигрыш в 10–50 раз только за счёт устранения дублирования.

Zero-copy парсинг

Ruff использует технику zero-copy parsin во многих местах. Вместо того чтобы копировать строки из исходного файла в отдельные строковые буферы, Ruff работает с исходным кодом через указатели и срезы. Это означает, что для анализа файла размером 1 МБ Ruff не выделяет 1 МБ дополнительной памяти — он работает напрямую с содержимым файла, отображая его в память через mmap.

Кеширование на уровне файлов

Кеш Ruff построен на основе хешей содержимого файлов (SHA-256). При первом запуске Ruff вычисляет хеш каждого файла и сохраняет результаты анализа. При повторном запуске Ruff проверяет хеш: если файл не изменился — результаты берутся из кеша. Кеш хранится в директории .ruff_cache и автоматически очищается при изменении конфигурации. Это особенно важно в CI-среде, где повторные запуски на тех же файлах — обычное дело.

Параллелизм через многопоточность

Ruff использует пул потоков (thread pool) для параллельной обработки файлов. Количество потоков по умолчанию равно количеству логических ядер процессора. Это означает, что на современном 8-ядерном процессоре Ruff проверяет 8 файлов одновременно. В отличие от многопроцессорности (multiprocessing), многопоточность в Rust не имеет проблем с GIL (Global Interpreter Lock), так как Rust не использует GIL. Это даёт практически линейное ускорение: на 8 ядрах Ruff работает примерно в 8 раз быстрее, чем на одном.

Алгоритмы и структуры данных

Ruff использует современные алгоритмы и структуры данных из экосистемы Rust. Например, для хранения множеств нарушений используется битовая маска (bitmask) вместо хеш-множества — это в десятки раз быстрее на операциях вставки и проверки. Для обхода AST используется итеративный подход с ручным управлением стеком вместо рекурсии — это устраняет риск переполнения стека на глубоко вложенных файлах и ускоряет обход за счёт локальности данных.

💡 Архитектура Ruff — предмет исследования для разработчиков инструментов. Многие идеи из Ruff (единый AST, zero-copy, битовые маски) постепенно перенимаются другими проектами.
📜

История Ruff и его создатели

Ruff был создан Чарли Маршем (Charlie Marsh) в 2022 году. До Ruff Чарли работал в сфере финансового ПО, но в свободное время экспериментировал с инструментарием для Python. Идея Ruff родилась из frustration: существующие инструменты были слишком медленными для больших проектов.

Первый публичный релиз Ruff состоялся 30 августа 2022 года. Уже к октябрю 2022 года проект собрал 5000 звёзд на GitHub. К концу 2022 года — 10 000 звёзд. В феврале 2023 года Чарли объявил о создании компании Astral и привлечении инвестиций в размере $4.5 млн от ведущих венчурных фондов. Основная цель компании — создание быстрых инструментов для Python на Rust.

В ноябре 2023 года Astral привлекла ещё $12 млн, а к 2024 году команда выросла до 20+ инженеров. В 2024 году Astral выпустила uv — менеджер пакетов для Python, который стал самым быстрорастущим инструментом в истории Python-экосистемы. Сам Ruff к этому моменту использовался в тысячах организаций и считался стандартом де-факто для линтинга Python.

Ключевые даты в истории Ruff:

  • Август 2022 — первый публичный релиз Ruff 0.0.0
  • Октябрь 2022 — 5000 звёзд на GitHub
  • Февраль 2023 — основание Astral, $4.5 млн инвестиций
  • Октябрь 2023 — Ruff 1.0 (стабилизация API)
  • Ноябрь 2023 — $12 млн дополнительных инвестиций
  • 2024 — uv, 20+ сотрудников, стандарт де-факто
  • 2025 — ty (инструмент для типов), интеграции, preview-режим
⚖️

Ruff vs традиционный подход

Вот как выглядит типичный процесс настройки качества кода без Ruff:

Традиционный подход (без Ruff)

  1. Установить flake8 + 10 плагинов (flake8-bugbear, flake8-bandit и т.д.)
  2. Установить black для форматирования
  3. Установить isort для сортировки импортов
  4. Установить pyupgrade для обновления синтаксиса
  5. Настроить каждый инструмент в отдельном конфиге (либо в .flake8, либо в black.toml, либо в setup.cfg, либо в pyproject.toml — у всех разный синтаксис!)
  6. Запускать их последовательно: flake8 && black --check && isort --check
  7. Ждать 10–30 секунд на каждый запуск

С Ruff

  1. pip install ruff (один пакет)
  2. Настроить в pyproject.toml (один раздел, единый синтаксис)
  3. Запустить ruff check && ruff format (одна или две команды)
  4. Получить результат за 0.1–0.5 секунд

Разница в процессе настройки и поддержки колоссальна. С Ruff вы тратите минуты, а не часы на конфигурацию, и секунды, а не минуты на ожидание.

Характеристика Без Ruff С Ruff
Количество зависимостей15–301 (ruff)
Конфигурационных файлов2–51 (pyproject.toml)
Время первого запуска (100K файлов)30–60 с0.2–0.5 с
Время повторного запуска30–60 с0.05–0.1 с (кеш)
Сложность настройкиВысокаяНизкая
Риск конфликтов плагиновВысокийМинимальный
👀

Ruff в действии — отзывы из сообщества

Вот что говорят о Ruff создатели популярных инструментов и разработчики из ведущих компаний:

Sebastián Ramírez — создатель FastAPI

«Ruff настолько быстр, что иногда я намеренно добавляю баг в код, чтобы убедиться, что он вообще запускается и проверяет код».

Nick Schrock — сооснователь GraphQL, создатель Dagster

«Почему Ruff меняет правила игры? Потому что он почти в 1000 раз быстрее. Буквально. Не опечатка. На нашем самом большом модуле (250K строк) pylint занимает 2.5 минуты. Ruff проверяет всю кодовую базу за 0.4 секунды».

Timothy Crosley — создатель isort

«Только что переключил свой первый проект на Ruff. Единственный минус: он настолько быстр, что я не мог поверить, что он работает, пока намеренно не ввёл несколько ошибок».

📋

Что дальше

В следующем уроке мы установим Ruff и убедимся, что он работает. А пока — вот ключевые выводы из этого урока:

📌 Что важно запомнить:

  • Ruff — линтер + форматировщик в одном бинарнике на Rust
  • Заменяет flake8, black, isort, pyupgrade, autoflake, bandit и 50+ плагинов
  • Работает в 10–100 раз быстрее аналогов
  • Используется в FastAPI, Pandas, Airflow и тысячах других проектов
  • Создан и поддерживается компанией Astral

Урок 1.1: Что такое Ruff и зачем он нужен

5 вопросов