VPSSpark Блог
← Вернуться к дневнику

CI мёртв, а GitHub этого не заметил

Заметки с сервера · Agent & CI #1 · 2026.06.08 · ~12 мин

Часто ищут: CI is dead · GitHub Actions agent loop · macOS runner queued

Разработчик и предупреждения CI, контекст agent retry loop
В 2026 CI больнее всего через queue, разброс Xcode и flaky retry.

Вероятно, вы ищете ответ на это

  • GitHub Actions macOS runner медленный / завис в Queued
  • iOS CI build падает или бесконечно retry
  • Xcode build в CI по таймауту, локально — норма
  • Cloud Mac vs GitHub Actions — что выбрать?
  • CI pipeline нестабилен, результат не воспроизводится

Если вы сопровождаете GitHub Actions или self-hosted macOS runner, в 2026 году жалобы звучат очень конкретно: длиннее queue, плавает время Xcode-сборки, один PR гоняют retry снова и снова, CI то зелёный, то красный. Статья разложена на четыре слоя — сначала инженерные симптомы, затем как агенты «зацикливают» CI, и наконец место Cloud Mac. Заголовок «CI мёртв» разберём в FAQ в конце; основной текст начинается с поломок, которые вы узнаёте сразу.

1 · Первый слой: почему GitHub Actions в 2026 «медленнее, нестабильнее, flaky»

За последние полгода от iOS-, Flutter- и macOS-команд мы слышим один и тот же паттерн — не «CI устарел как идея», а одновременный рост четырёх классов проблем ниже.

Queued
macOS job долго в очереди
±40%
Разброс wall time Xcode на ветке
3×+
Запусков workflow на один PR

1.1 Очередь macOS runner

На hosted macos-latest время в Queued часто больше, чем сам build. В таймлайне job: 40 минут ожидания, 12 минут работы — команда всё ещё крутит флаги xcodebuild. Формула диагностики по-прежнему wait time >> run time, подробно в runbook по очереди macOS runner. В 2026 queue растёт, потому что лимит macOS concurrency не успевает за числом job в репозитории — и потому что Archive и тяжёлые задачи занимают слоты, утягивая в очередь быстрый feedback по PR.

1.2 Разброс времени Xcode build

Тот же commit, перезапуск: в CI Xcode то 18, то 31 минута, на локальном Mac стабильно ~15. Типичные факторы: cold start runner, промах DerivedData cache, повторный resolve CocoaPods, patch Xcode в образе не совпадает с локальной машиной. По отдельности это похоже на «кэш настроен криво» — но когда каждый retry — холодная среда, разброс превращается в «CI нельзя доверять».

1.3 Retry вышли из-под контроля

Помимо явного retry-on-failure в workflow, растут неявные retry: агент или бот читает логи → патч → push → снова Actions. PR из «2 push от человека» превращается в «8 push от машины»; счёт minutes и нагрузка на queue растут вместе. Кажется flaky test — на деле один PR в CI гоняют с разным кодом в нескольких раундах.

1.4 Flaky CI: то зелёный, то красный, сложно воспроизвести

Классика: sporadic timeout тестов, сбой старта симулятора, блокировка keychain при подписи. В 2026 добавился слой: каждый раунд агента даёт другой diff — трудно ответить «flaky test или агент сломал другое». Фраза, от которой больнее всего release-инженерам: «Вчера вечером CI был зелёный, сегодня утром тот же tag снова красный.»

Что видите Часто думают Сначала проверить
Job долго в Queued GitHub сломался macOS concurrency, Archive в PR?
Время Xcode плавает Проект разросся Кэш, образ Xcode, cold start
Несколько run на PR Хаотичные push Retry агента/бота, нет concurrency
То зелёный, то красный Плохие тесты Commit одинаков в раунде? среда дрейфует?

2 · Второй слой: не «CI стал хуже», а CI стал зацикленным

Чинить queue, кэш и тесты по отдельности часто помогает на один круг. Вместе видна общая нить: CI — уже не разовая проверка, а цикл «сбой → фикс → снова гонять». До агентов цикл жил в голове инженера; теперь он в инфраструктуре — модель читает логи, выдаёт patch, автоматически триггерит workflow.

Типичная цепочка давно обыденна:

  • PR открыт → CI красный (тест / сборка)
  • Агент читает логи Actions → fix commit
  • Push → новый workflow → снова красный → ещё fix
  • Пока не зелёный — или пока человек не остановит / не кончатся tokens

Формально это GitHub Actions / CI; по факту — agent retry loop. Вы боретесь не с «одним упавшим build», а с вероятностным итогом множества попыток — отсюда симптомы слоя 1: queue забита повторными job, время Xcode дрейфует из-за cold start, flaky потому что код и среда меняются каждый раунд.

Здесь полезна чуть абстрактная, но практичная формулировка: классический CI предполагает детерминизм — тот же commit, та же среда, воспроизводимый результат. После цикла агента путь становится вероятностным — на какой попытке зелёный, сколько commit между, случайно ли сработал Archive. Это объясняет, почему «просто добавить кэш» не решает всё.

Измерение Классический CI (разовая проверка) Зацикленный CI (agent retry loop)
Число триггеров Мало, от push человека Автоповторы, ×N
Версия кода Голова PR стабильна Commit меняется в цикле
Смысл красного Текущий код сломан Может, «ещё мало попыток»
Стоимость Minutes × тариф Minutes + tokens + cold start среды

GitHub по-прежнему улучшает workflow, runner и кэш — под одиночные детерминированные job. Когда в репозитории по умолчанию крутится agent loop, это помогает, но не останавливает мультипликатор «число job × раунды retry». Поэтому в заголовке «GitHub этого не заметил»: продуктовый нарратив всё ещё CI/CD, а использование уходит в автоматический цикл починки.

3 · Третий слой: структура изменилась — от CI pipeline к retry loop + execution substrate

Симптомы (слой 1) и причина (слой 2) вместе: CI из линейного pipeline превращается в систему исполнения с обратной связью.

Рис. 1 · Зацикленный CI: решение агента + исполнение runner + feedback

Developer intentionтесты · lint · границы релиза
AI Agentчитать логи · патч · ретриггер
Execution substrateRunner / Cloud Mac · сборка · подпись
Retry loopсбой → фикс → снова гонять

Старая модель: Code → Build → Test → Result — сбой останавливает линию. Новая: Code → Agent → Modify → Execute → Retry → … → Result — сбой часть цикла, не конец. Зелёная галочка в GitHub ещё успокаивает, но смысл другой — может зелёный только с 4-й попытки, с изменёнными commit между.

Новый, но инженерный термин: execution substrate (база исполнения) — агент может менять код, но компиляция, подпись и upload должны лечь на стабильную воспроизводимую macOS-площадку. Serverless job слишком короткий, state не уносится; локальный Mac засыпает и обновляет Xcode; hosted runner стоит в queue и дрейфует по spec. Cloud Mac закрывает именно этот слой: постоянно online, toolchain можно pin, среду можно снапшотить — не «удалённый рабочий стол», а слой retry loop, который должен оставаться максимально детерминированным.

Власть исполнения смещается: раньше человек писал workflow, машина выполняла; теперь человек задаёт границы (что в PR, что в Archive, сколько retry), агент пробует пути внутри границ, человек принимает итог. macOS/iOS-команды чувствуют это острее — подпись и Archive не должны бесконечно крутиться в retry loop, иначе зелёный ≠ готов к релизу.

Ключевая мысль (слой 3)
CI не исчез — он из инструмента разовой проверки стал циклическим пространством исполнения. Агент решает, что менять и сколько раз пробовать; Runner / Cloud Mac — где гонять и дрейфует ли среда. Разделив два слоя, объясняются queue, разброс Xcode и flaky.

4 · Четвёртый слой: стабилизировать execution surface через Cloud Mac (можно сразу)

Не нужно ждать новый нарратив GitHub и не нужно сносить Actions. Против зацикленного CI у клиентов VPSSpark чаще всего срабатывают четыре меры ниже — и это отличие Cloud Mac от hosted runner.

4.1 Разделение пулов: ограничить радиус retry

На PR только L0/L1 (analyze, unit tests, simulator build), Archive в PR запрещён; release, IPA и нотаризация — только в изолированных пулах на main/tag. Как бы ни крутился agent loop — 35-минутный Archive не забьёт fast pool и не поставит всю команду в Queued. Жёсткие правила в CI Hard Rules; топология двух пулов Flutter в 2 Cloud Mac: fast/archive.

4.2 Warm environment: без cold start на каждый retry

Держать PUB_CACHE, DerivedData, кэш загрузки Pods персистентно; runner autostart, online 7×24. На 2-м retry агента не должно быть 15 минут pod install — иначе разброс Xcode читают как «проект тормозит». Cloud Mac покупает стоимость удержания среды, а не только CPU-minutes за job.

4.3 macOS execution substrate: зафиксировать версии toolchain

Pin Flutter/Xcode major через образ или fvm; машина Archive и fast pool физически разделены, без общего DerivedData. Каждый раунд retry должен идти на том же Distribution-сертификате, тех же CLT — условие аудируемого iOS CI. Границы self-hosted runner: документация GitHub.

4.4 Retry isolation: потолок для loop

На уровне workflow: concurrency отменяет старые run того же PR; отдельные timeout и лимит push для agent-триггеров; машина подписи только для release pool. Синтаксис: документация workflow. Цель не запретить агентов, а держать loop в контролируемых границах.

PoC на 1–2 дня
Одна Cloud Mac как пул macos-fast; hosted runner пока на Archive. Три дня смотреть P95 queue и дисперсию wall time Xcode. Стабильно? Добавить вторую Archive-машину — как в серии «2 машины на старт», мотив расширен от queue к agent retry.

5 · FAQ

«CI мёртв» — это паника?

Заголовок намеренно резкий, явление реальное: pipeline может быть зелёным, PR мержатся — и при этом «тот же код, те же проверки, но путь и результат больше не стабильно предсказуемы». «CI мёртв» не значит, что GitHub Actions бесполезен, а что классическое допущение — сборка и проверка как детерминированный процесс — не держится, когда агенты меняют код и снова триггерят workflow. Точнее: CI жив, сменилась семантика — от continuous integration к continuous attempt.

GitHub переделает продукт из-за этого?

Да, но темп может отставать от практики. Вы по-прежнему увидите оптимизацию workflow, ёмкость runner, кэш — всё под классический CI. Agent-возможности (sandbox, аудит, биллинг по tokens) скорее придут поэтапно, чем новым нарративом за ночь. Командам не обязательно ждать официального определения: разделить пулы PR/Archive, ограничить retry, заблокировать машину подписи — дешёвые ограждения в эпоху агентов.

Cloud Mac vs hosted macOS runner?

Коротко: hosted runner — аренда времени одного job; Cloud Mac — долгоживущая стабильная среда. Редкие релизы, queue терпим, job короткие — macos-latest часто хватает. Agent loop или частый iOS CI: нужны Xcode/сертификаты/кэш резидентно, fast и Archive физически разделены, без обрыва от sleep или тихого апгрейда Xcode. Cloud Mac окупается на подписи, Archive, нотаризации — каждый retry на том же ключе, той же toolchain, а не рулетка cold start.

Связь с OpenClaw / локальными агентами?

Не конфликт, разные слои. OpenClaw, Cursor Agent, локальный Copilot решают, что менять и как оркестрировать задачи — gateway и scheduling. Runner / Cloud Mac решают, где и в какой среде собирать, тестировать, подписывать, заливать. Агент может патчить локально или крутиться в CI — macOS-сборка в конце должна лечь на воспроизводимую execution surface. Разделение orchestration и execution убирает «агент умный, а CI каждый раз с нуля в чужой среде».

Следующий шаг слоя 4: одна Cloud Mac как фиксированный substrate

Если queue, дрейф Xcode, взрыв retry и flaky из первых трёх слоёв знакомы — слой 4 не обязан решить всё сразу. Самый частый путь: одна Cloud Mac как warm fast pool, чтобы приглушить cold start и дрейф toolchain в agent retry; Archive и подпись изолировать по необходимости. Apple Silicon с низким потреблением подходит для постоянной работы; для iOS/macOS-команд это бьёт в структуру счёта зацикленного CI точнее, чем ещё пакеты GitHub minutes.

Если используете статью как PoC-чеклист: VPSSpark Cloud Mac mini как старт macOS execution substrate — смотреть тарифы, сначала стабилизировать среду, потом отпускать агент на N-й раунд.

Акция

Семантика CI сменилась? Сначала стабилизируйте среду

Agent loop · Cloud Mac · разделение пулов

На главную
Акция Смотреть тарифы