← Назад к вопросам

Как на прошлом месте работы предоставляли prod версию приложения пользователю?

1.2 Junior🔥 142 комментариев
#CI/CD и инструменты разработки

Комментарии (2)

🐱
deepseek-v3.2PrepBro AI5 апр. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Процесс поставки продакшен-версии приложения пользователям на моем предыдущем месте работы

На предыдущем проекте (крупное fintech-приложение для iOS с миллионами пользователей) мы использовали строго регламентированный процесс Continuous Delivery (CD) с акцентом на стабильность, безопасность и контроль качества. Вот детальное описание шагов.

1. Подготовка и сборка (Build Preparation)

Перед сборкой продакшен-версии выполнялся ряд обязательных проверок:

  • Фиксация кода: Все изменения, предназначенные для релиза, мержались в защищенную ветку release/X.X.X. Далее эта ветка блокировалась для любых новых коммитов, кроме критических хотфиксов.
  • Проверка зависимостей: Проводился аудит Podfile.lock или Package.resolved на предмет наличия нелицензионных или уязвимых зависимостей с помощью внутренних скриптов и cocoapods-keys для шифрования чувствительных данных.
  • Конфигурация сборки: Использовалась отдельная Scheme & Configuration (Release-AppStore) с отключенными логи уровня Debug, включенными оптимизациями компилятора (Optimization Level = -Osize), активированным Bitcode и специальным Info.plist, где:
    *   `ITSAppUsesNonExemptEncryption` устанавливался в `false` для экспортного соответствия.
    *   Отключались все `DEBUG`-макросы и инструменты разработчика.

2. Автоматизированная сборка и подписание (Automated Build & Signing)

Сборка происходила на выделенном Mac mini в рамках CI/CD-пайплайна (использовался GitLab CI):

# Упрощенный пример шага в .gitlab-ci.yml
build_production_ios:
  stage: deploy
  script:
    - bundle install
    - bundle exec fastlane build_production
  only:
    - /^release\/.*$/  # Триггерился только на release-ветки

Fastlane был ядром процесса. Вот ключевые действия внутри Fastfile:

# Fastlane lane для сборки продакшена
lane :build_production do
  # 1. Увеличиваем build number
  increment_build_number(
    build_number: latest_testflight_build_number + 1
  )

  # 2. Собираем и подписываем архив
  gym(
    scheme: "Release-AppStore",
    export_method: "app-store",
    export_options: {
      provisioningProfiles: {
        "com.company.appname" => "App Store Distribution Profile"
      }
    },
    silent: true,
    clean: true
  )

  # 3. Загружаем в TestFlight для внутреннего тестирования
  pilot(skip_submission: true, notify_external_testers: false)
end

Подписание осуществлялось автоматически с помощью Match (также часть Fastlane), который хранил сертификаты и профили в зашифрованном Git-репозитории, обеспечивая консистентность между всеми разработчиками и CI-сервером.

3. Многоуровневое тестирование (Multi-Stage Testing)

  1. Внутреннее бета-тестирование (TestFlight): Сразу после сборки IPA загружалась в App Store Connect как новая build-версия для внутренних тестеров (разработчики, QA, продакт-менеджеры). Это позволяла провести смоук-тест на реальных устройствах.
  2. Внешнее бета-тестирование: После одобрения внутренней командой, build продвигался для внешних тестеров (закрытая группа доверенных пользователей). Мы собирали обратную связь через TestFlight-комментарии и внутренние аналитические инструменты.
  3. Автоматические проверки: Параллельно запускались UI-тесты на браузерах Sauce Labs и проводилась проверка на соответствие App Store Review Guidelines с помощью инструментов типа App Store Connect API.

4. Контроль качества и релиз (Quality Gate & Release)

Перед финальным релизом в App Store проводился релиз-митинг с участием тимлидов (разработка, QA, безопасность, поддержка). На нем:

  • Проверялись результаты всех тестов.
  • Утверждались релиз-ноты (что нового, что исправлено).
  • Принималось решение о «зеленом свете» для публикации.

Финальный шаг выполнялся вручную через App Store Connect или автоматически через fastlane deliver:

lane :release_to_app_store do
  # Завершаем процесс отправки на ревью
  deliver(
    submit_for_review: true,
    automatic_release: false, # Ручной релиз после одобрения
    force: true,
    precheck_include_in_app_purchases: false
  )
end

Мы предпочитали ручной релиз после одобрения Apple (не automatic), чтобы иметь возможность точечно отреагировать на потенциальные замечания ревьюверов или отозвать build, если в последний момент обнаруживалась критическая проблема.

Ключевые принципы процесса

  • Повторяемость: Все шаги, кроме финального бизнес-решения о выпуске, были автоматизированы.
  • Безопасность: Ключи подписи никогда не хранились в явном виде, доступ к продакшен-сборкам строго контролировался.
  • Наблюдаемость: Каждой сборке сопоставлялся тег в Git, записи в Jira и отчеты из CI/CD.
  • Откат (Rollback): Стратегия отката предусматривала либо экстренный хотфикс, либо, в крайнем случае, откат на предыдущую версию через App Store (сложная и длительная процедура, поэтому мы делали всё, чтобы её избежать).

Такой подход минимизировал человеческий фактор, обеспечивал стабильность и позволял выпускать обновления примерно раз в 2-3 недели.

Как на прошлом месте работы предоставляли prod версию приложения пользователю? | PrepBro