惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

雷峰网
雷峰网
G
Google Developers Blog
D
Docker
The GitHub Blog
The GitHub Blog
H
Help Net Security
WordPress大学
WordPress大学
博客园_首页
Recent Announcements
Recent Announcements
P
Proofpoint News Feed
罗磊的独立博客
I
InfoQ
U
Unit 42
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
V
Visual Studio Blog
Jina AI
Jina AI
J
Java Code Geeks
博客园 - Franky
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
大猫的无限游戏
大猫的无限游戏
小众软件
小众软件
Last Week in AI
Last Week in AI
钛媒体:引领未来商业与生活新知
钛媒体:引领未来商业与生活新知
D
DataBreaches.Net
Google DeepMind News
Google DeepMind News

Все публикации подряд на Хабре

Ловим музу за клавиатуру: как айтишнику стать автором Что умеет Midjourney в 2026? Мой немного грустный разбор этого шикарного инструмента Никто не любит писать тесты, но ИИ может исправить это IPv8 выглядит как мечта. Поэтому почти наверняка не взлетит Производители вернули в продажу материнки с DDR3. Что происходит? Управление агентом с телефона через Telegram теперь в KodaCode От координации к лидерству: как меняется роль руководителя разработки Я сделала родителям бизнес вместо пенсии: зарабатываем 70 тысяч, мама не даёт продать В три раза быстрее приемка товара и оптимизация трудозатрат на 73%: как «РСТ-Инвент» помог Gulliver Group ИИ-шечный мир победил? О влиянии искусственного интеллекта на игропром Кремль снижает давление на Телеграмм пока Европа строит интернет по паспорту Как CEO, CTO и CIO за 8 часов собрали ИИ-директора, который умеет держать позицию под давлением Как (не) потерять домен за выходные Вместо 8 разных VPS: как я организовал практику студентам на одном сервере Почему твой Open Source проект не замечают? R&D: искусство управления неопределенностью в разработке AI-дефляция: вакансий для разработчиков больше, а рост зарплат — худший за 15 лет Мы отдали управление роботами OpenClaw. Что из этого вышло Галактический ID: система идентификации для всех форм разумной жизни Шесть основ бизнес-анализа: начинаем с вопроса «Кто в игре?» Код-ревью, в котором дело не в коде Данные переехали. Команда — нет Системной подход к сдаче OSWE в 2025 Почему комната управления реактором покрашена в цвет морской пены 4 YAML-файла вместо PySpark: как аналитикам строить пайплайны без разработчиков LLM-агент для поиска свободных доменов: автоматизируем подбор Когда, зачем и как правильно начинать новую сессию в Claude Code? Как я заставил нейросеть писать макросы для FreeCAD Анатомия ИИ‑агента для подбора персонала. От тысячи резюме к топ‑10 за минуты Опыт разработчика как экономика внимания
Python-проект в 2026: uv, ruff, pyproject.toml. Настраива...
Ragnar Lodbrog · 2026-06-07 · via Все публикации подряд на Хабре

pip install, requirements.txt, virtualenv, black, isort, flake8, mypy, setup.py... Если вы настраиваете Python-проект так же, как в 2020 году, эта статья для вас. Показываю современный стек, который заменяет всё вышеперечисленное.

В 2026 году экосистема Python-инструментов наконец собралась в нечто цельное. Два инструмента (uv и ruff) + один файл (pyproject.toml) заменяют 7+ отдельных утилит. Вот как это работает.

Что заменяем и на что

Было

Стало

pip + pip-tools

uv

virtualenv / venv

uv

pyenv

uv

poetry / pipenv

uv

black (форматирование)

ruff format

isort (сортировка импортов)

ruff

flake8 (линтинг)

ruff check

setup.py / setup.cfg

pyproject.toml

requirements.txt

pyproject.toml + uv.lock

Два инструмента вместо девяти. Оба написаны на Rust, оба от Astral. Работают в 10-100 раз быстрее аналогов на Python.

Шаг 1. Установка uv

Одна команда:

# macOS / Linux
curl -LsSf https://astral.sh/uv/install.sh | sh

# Windows
powershell -ExecutionPolicy ByPass -c "irm https://astral.sh/uv/install.ps1 | iex"

# Или через pip (если хочется по-старому)
pip install uv

Проверяем:

$ uv --version
uv 0.7.x

ruff ставить отдельно не нужно. uv умеет запускать его через uvx ruff. Но если хотите глобально:

uv tool install ruff

Шаг 2. Создаём проект

$ uv init myproject
Initialized project `myproject` at `./myproject`

$ cd myproject
$ ls
pyproject.toml  src/  README.md  .python-version

uv создал структуру проекта с pyproject.toml, папку src/ и файл .python-version. Никаких setup.pyrequirements.txtMakefile.

Если нужен Python конкретной версии:

# uv сам скачает и установит нужную версию Python
uv python install 3.13
uv python pin 3.13

Да, uv заменяет pyenv. Он сам управляет версиями Python.

Шаг 3. Зависимости

Забудьте pip install. Теперь так:

# Добавить зависимость
uv add requests
uv add pandas numpy

# Добавить dev-зависимость
uv add --dev pytest ruff

# Удалить зависимость
uv remove pandas

uv автоматически:

1. Создаёт виртуальное окружение (если его нет).
2. Добавляет пакет в pyproject.toml.
3. Обновляет lock-файл uv.lock.
4. Устанавливает пакет.

Всё за одну команду. Никаких pip freeze > requirements.txt.

Скорость

uv устанавливает пакеты в 10-100 раз быстрее pip. Холодная установка numpy + pandas + requests:

Инструмент

Время

pip

~12 сек

poetry

~8 сек

uv

~0.5 сек

Это не опечатка. uv кэширует пакеты глобально и использует жёсткие ссылки вместо копирования файлов.

Шаг 4. pyproject.toml

Вот как выглядит типичный pyproject.toml после настройки:

[project]
name = "myproject"
version = "0.1.0"
description = "My awesome project"
readme = "README.md"
requires-python = ">=3.12"
dependencies = [
    "requests>=2.32",
    "numpy>=2.0",
]

[dependency-groups]
dev = [
    "pytest>=8.0",
    "ruff>=0.9",
]

[tool.ruff]
target-version = "py312"
line-length = 88

[tool.ruff.lint]
select = [
    "E",    # pycodestyle errors
    "W",    # pycodestyle warnings
    "F",    # pyflakes
    "I",    # isort
    "UP",   # pyupgrade
    "B",    # flake8-bugbear
    "SIM",  # flake8-simplify
]

[tool.ruff.format]
quote-style = "double"

[tool.pytest.ini_options]
testpaths = ["tests"]

Один файл. Зависимости, линтер, форматтер, тесты. Всё здесь.

Шаг 5. Линтинг и форматирование (ruff)

ruff заменяет flake8 + black + isort + pyupgrade. Одна команда вместо четырёх.

# Проверить код
uvx ruff check .

# Проверить и автоматически исправить
uvx ruff check --fix .

# Отформатировать код (замена black)
uvx ruff format .

# Проверить форматирование без изменений
uvx ruff format --check .

Скорость ruff

ruff проверяет код в 10-100 раз быстрее flake8. На проекте из 1000 файлов:

Инструмент

Время

flake8

~12 сек

flake8 + isort + black

~25 сек

ruff check + ruff format

~0.3 сек

Пример: что ruff ловит

# До
import os
import sys
from typing import Optional, List, Dict
import json

def process(data: Optional[List[Dict[str, str]]] = None):
    if data == None:
        data = list()
    for item in data:
        if len(item.keys()) > 0:
            print(item)
# После ruff check --fix + ruff format
import json

def process(data: list[dict[str, str]] | None = None):
    if data is None:
        data = []
    for item in data:
        if item:
            print(item)

Что ruff сделал:

1. Убрал неиспользуемые импорты (ossys).
2. Отсортировал оставшиеся импорты.
3. Заменил Optional[List[Dict]] на list[dict] | None (Python 3.10+).
4. Заменил == None на is None.
5. Заменил list() на [].
6. Упростил len(item.keys()) > 0 до item.

Шаг 6. Запуск скриптов

Для запуска скриптов внутри виртуального окружения:

# Запуск скрипта
uv run python src/myproject/main.py

# Запуск тестов
uv run pytest

# Запуск любой команды в окружении
uv run mycommand

uv run автоматически активирует виртуальное окружение. Не нужно никаких source .venv/bin/activate.

Одноразовые скрипты

Нужно быстро запустить скрипт с зависимостями, не создавая проект?

# Запустить скрипт, который требует requests, без установки
uv run --with requests python script.py

# Запустить инструмент одноразово (npx-стиль)
uvx black .
uvx httpie https://api.github.com

uvx = npx для Python. Скачивает, запускает, не засоряет систему.

Шаг 7. CI/CD

Минимальный GitHub Actions workflow:

# .github/workflows/ci.yml
name: CI
on: [push, pull_request]

jobs:
  check:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: astral-sh/setup-uv@v5

      - run: uv sync
      - run: uvx ruff check .
      - run: uvx ruff format --check .
      - run: uv run pytest

4 строки. Установка зависимостей, линтинг, форматирование, тесты. Всё.

Время CI на типичном проекте:

Стек

Время

pip + flake8 + black + pytest

~45 сек

poetry + flake8 + black + pytest

~60 сек

uv + ruff + pytest

~12 сек

Шаг 8. Docker

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

FROM python:3.13-slim

# Установить uv
COPY --from=ghcr.io/astral-sh/uv:latest /uv /usr/local/bin/uv

# Копировать файлы проекта
WORKDIR /app
COPY pyproject.toml uv.lock ./

# Установить зависимости (кэшируется Docker layer)
RUN uv sync --no-dev --frozen

# Копировать код
COPY src/ src/

CMD ["uv", "run", "python", "-m", "myproject"]

Важный момент: pyproject.toml и uv.lock копируются отдельно от кода. Это позволяет Docker кэшировать слой с зависимостями. Если код изменился, а зависимости нет, переустановки не будет.

Миграция с pip/poetry за 2 минуты

С requirements.txt

# Инициализировать проект
uv init

# Импортировать зависимости из requirements.txt
uv add $(cat requirements.txt)

С poetry

uv понимает pyproject.toml в формате Poetry. Просто:

# Удалить poetry.lock, создать uv.lock
rm poetry.lock
uv lock
uv sync

Если в pyproject.toml есть секция [tool.poetry], uv прочитает зависимости оттуда.

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

# 1. Создать проект
uv init myproject && cd myproject

# 2. Добавить зависимости
uv add requests pydantic

# 3. Добавить dev-зависимости
uv add --dev pytest ruff

# 4. Написать код
# ...

# 5. Проверить и отформатировать
uvx ruff check --fix .
uvx ruff format .

# 6. Запустить тесты
uv run pytest

# 7. Готово

Пять минут. Никаких setup.pyMANIFEST.inrequirements.txttox.ini.flake8.isort.cfgpyproject.toml на 200 строк.

uv + ruff + pyproject.toml = всё, что нужно для Python-проекта в 2026 году.

Ссылки

uv на GitHub (80k+ звёзд)
ruff на GitHub (40k+ звёзд)
Документация uv
Документация ruff
PEP 621: стандарт pyproject.toml