CI/CD

Материал из llmdocs — справочник разработчика
Портал: Git, CI/CD, DevOps
CI/CD
CIнепрерывная интеграция
CDнепрерывная поставка (delivery) или развёртывание (deployment)
Истокиэкстремальное программирование (конец 1990-х)
Ключевые текстыМартин Фаулер «Continuous Integration» (2000), Хамбл и Фарли «Continuous Delivery» (2010)
ИнструментыGitHub Actions, GitLab CI, Jenkins, CircleCI, Argo CD
МетрикиDORA (частота развёртываний, время выполнения изменений, доля неудачных изменений, время восстановления)

CI/CD — набор практик автоматизации, при котором каждое изменение кода автоматически собирается, проверяется и доводится до пользователей. CI (Continuous Integration, непрерывная интеграция) — разработчики часто вливают изменения в общую ветку, и каждое вливание запускает сборку и тесты. CD — либо Continuous Delivery (непрерывная поставка: любая проверенная версия готова к выкладке одной кнопкой), либо Continuous Deployment (непрерывное развёртывание: каждое изменение, прошедшее проверки, выкладывается в продакшен автоматически).

Цель — короткий и надёжный путь от коммита до работающего продукта: ошибки находятся через минуты после появления, а выкладка становится рутинной операцией, а не рискованным событием раз в квартал.

История

Термин «непрерывная интеграция» употребил Грейди Буч в 1991 году, а практикой его сделало экстремальное программирование Кента Бека в конце 1990-х. Широкую известность принесла статья Мартина Фаулера «Continuous Integration» (2000, с последующими редакциями).[1] Инструменты появились тогда же: CruiseControl (2001), Hudson (2005), который в 2011 году после конфликта с Oracle продолжил развиваться как Jenkins.[6]

В 2010 году Джез Хамбл и Дэвид Фарли выпустили книгу «Continuous Delivery», описавшую конвейер развёртывания (deployment pipeline).[2] В 2010-х CI переехала в облака и в сами платформы хостинга кода: Travis CI, CircleCI, GitLab CI, а с 2019 года — GitHub Actions.

Конвейер

Конвейер (pipeline) — последовательность этапов, которые проходит каждое изменение:

Этап Что происходит
Триггер push в ветку, открытие pull request, тег, расписание
Сборка установка зависимостей, компиляция, сборка образа по Dockerfile
Статические проверки линтеры, форматирование, проверка типов, поиск секретов и уязвимостей
Тесты модульные, интеграционные, сквозные
Публикация артефакта образ в реестр, пакет, бинарник с версией
Развёртывание тестовое окружение → продакшен
Проверка после выкладки смоук-тесты, мониторинг, автоматический откат

Если любой этап падает, конвейер останавливается, а автор изменения получает уведомление. Важный принцип — артефакт собирается один раз и без изменений проходит все окружения: в продакшен попадает ровно то, что тестировали.

Пример

Конвейер GitHub Actions для проекта на Python:[4]

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

jobs:
  test:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: astral-sh/setup-uv@v6
      - run: uv sync --locked
      - run: uv run ruff check .
      - run: uv run pytest --maxfail=1

  deploy:
    needs: test
    if: github.ref == 'refs/heads/main'
    runs-on: ubuntu-latest
    environment: production
    steps:
      - uses: actions/checkout@v4
      - run: ./scripts/deploy.sh
        env:
          DEPLOY_KEY: ${{ secrets.DEPLOY_KEY }}

В GitLab CI аналогичное описание хранится в файле .gitlab-ci.yml со стадиями stages.[5] Конвейер — такой же код, как приложение: он версионируется в Git и проходит ревью.

Стратегии развёртывания

  • Rolling update — экземпляры заменяются новыми по очереди; так по умолчанию обновляет Kubernetes.
  • Blue-green — новая версия поднимается рядом со старой, и трафик переключается целиком; откат — переключение обратно.
  • Canary — новая версия сначала получает небольшую долю трафика; при росте ошибок выкладка останавливается.
  • Флаги функций — код выкладывается выключенным и включается для части пользователей независимо от развёртывания.

Инфраструктуру, в которую идёт выкладка, тоже описывают кодом и меняют через конвейер — см. Infrastructure as Code. В подходе GitOps желаемое состояние кластера хранится в репозитории, а агенты вроде Argo CD или Flux синхронизируют с ним кластер.

Как измерять

Исследовательская программа DORA выделила четыре ключевые метрики эффективности поставки:[3]

  1. Частота развёртываний — как часто изменения попадают в продакшен.
  2. Время выполнения изменений (lead time) — от коммита до продакшена.
  3. Доля неудачных изменений — какой процент выкладок требует исправления или отката.
  4. Время восстановления после неудачного развёртывания.

Исследования DORA показывают, что скорость и стабильность не противоречат друг другу: команды, выкладывающие чаще и меньшими порциями, как правило, реже ломают продакшен.

Хорошие практики

  • Быстрый конвейер: проверки pull request должны укладываться в минуты; медленные тесты распараллеливают и кэшируют зависимости.
  • Сломанная основная ветка — главный приоритет команды.
  • Секреты — только в хранилище секретов CI, а не в репозитории; права токенов развёртывания — минимальные.
  • Нестабильные (flaky) тесты чинить или изолировать: иначе к красным сборкам привыкают и перестают их замечать.
  • Версии релизов — по правилам семантического версионирования.

См. также

Источники

  1. Martin Fowler — Continuous Integration
  2. Jez Humble — Continuous Delivery
  3. DORA — DORA's software delivery metrics
  4. GitHub Docs — GitHub Actions
  5. GitLab Docs — CI/CD
  6. Jenkins