Так получилось, что инструменты DevOps обычно иллюстрируются на примере CI/CD какого-то масштабного веб-сервиса. Отчасти так получилось по историческим причинам, отчасти свою роль сыграли замечательные книги типа Google SRE Book.
К черту, давайте посмотрим на что-нибудь действительно новое. На Mobius 2017 к нам приезжает Jing Li из Viacom, с докладом «Android meets Docker».
Накануне конференции удалось найти несколько минут в его плотном графике и задать пару вопросов. В этом интервью Jing рассказывает о DevOps в мобильной разработке, приводит примеры задач и дает конкретные рекомендации по улучшению вашего DevOps процесса.
— Привет. Расскажи Хабру о себе. Где ты работаешь, чем занимаешься?
— Раньше был разработчиком в компаниях Sony, Nokia, eBay и Viacom (они — хозяева MTV, Paramount Pictures и так далее). В данный момент я готовлюсь к следующему большому приключению, отдыхаю дома и работаю над своими open source-проектами (https://github.com/thyrlian). Информационные технологии сейчас развиваются очень быстро, каждый день нужно изучать слишком много нового. Поэтому после работы я стараюсь заниматься машинным обучением и виртуальной реальностью .
— Как ты попал в мобильную разработку? Ты занимаешься DevOps на постоянной основе или это была какая-то разовая работа?
— Так же как дети любят играть на игровых приставках, я пристрастился к мобильнику еще со школы, когда трава была зеленее, а экраны — монохромными. Понятно, что после окончания университета я сразу же занялся мобильной разработкой. В мобильной разработке DevOps происходит каждую минуту, в особенности, когда кто-то заливает изменения в код. Так же как в обычной разработке, DevOps требует большой работы по написанию кода, правильной архитектуры и сложных конфигураций. Учитывая комбинацию этих трех аспектов, сложно сказать, что это какая-то одноразовая работа. Это постоянный процесс, свой прогресс в котором можно отслеживать по множеству вполне конкретных признаков:
- Скорость — время твоей реакции должно быть такое, чтобы разработчикам не приходилось ждать ответа слишком долго;
- Стабильность — никто не хочет работать с разваливающейся системой, это потеря времени;
- Надежность — результаты должны быть достаточно качественные и достоверные, никаких ложных срабатываний;
- Консистентность — результаты не должны отличаться между несколькими попытками запуска, или между разными машинами;
- Гибкость — использование модульных систем позволяет писать код один раз, а запускать его — везде (Jenkins, CircleCI и т.п.);
- Унификация — нужно избавляться от языковых барьеров и использовать один универсальный язык для склеивания разных частей системы;
- Масштабируемость — при возможности параллельного выполнения задач необходимо выбирать правильные пути разрешения инженерных компромиссов;
- Воспроизводимость — никогда не терять контроля над конфигурациями системы контроля версий.
Часто вижу, как люди раз за разом жмут кнопку «перезапустить сборку» в надежде, что сборка позеленеет. Это происходит как раз из-за проблем со стабильностью, надежностью и консистентностью.
— Как именно DevOps на мобильных платформах отличается от того, что происходит при разработке веб-сервисов (типа Google) или десктопных приложений? Есть ли в нем что-то особенное?
— Тулчейны для традицинной разработки: бэкенд, фронтенд, десктоп — они достаточно функциональны и выполняются нативно. На мобилках же нужно выбирать между запуском на компьютере или на мобильной платформе. Которая, в свою очередь, может быть как физическим устройством, так и симулятором. Кроме среды, существуют зависимости на различные сторонние сервисы. Наиболее общая часть — это публикация: Google Play, App Store или какой-то из сервисов публикации типа HockeyApp или Fabric. Для каждого из этих сервисов существуют консольные утилиты, которые можно использовать в автоматизации. С другой стороны, можно использовать инструменты типа Fastlane. Часто нужно заботиться и о побочных задачах. Одна из основных задач — дизайн. Например, нужно решить, как простым образом автоматически импортировать и конвертировать дизайнерские ресурсы. Если приложение работает в нескольких странах — можно встретиться с задачей синхронизации локализаций с сервисов коллективного перевода типа Crowdin или POEditor. Это еще не вся головная боль — например, мы захотели мониторить производительность приложения после публикации. Или вот, каким образом получить оценки и отзывы пользователей? Как отобразить в виде графиков на большом мониторе, висящем на стене? Все эти данные получаются со внешних сервисов, интегрировать их между собой совсем не просто.
— У тебя всегда в запасе интересные истории. Расскажи о какой-нибудь задаче, которую тебе пришлось девопсить для мобильной платформы? Лучше что-нибудь не по теме доклада, чтобы сохранить интригу.
— В те времена, когда Google еще не выпустили Android 6.0 Marshmallow, система во время установки просила пользователя предоставить соответствующие разрешения. Если же новая версия приложения хотела расширенных прав, приложение не могло автоматически обновиться — вначале система запрашивала у пользователя разрешение на этот расширенный набор прав. Однажды это случилось и в нашей команде — мы добавили какую-то библиотеку, которая внезапно втихую добавила какие-то дополнительные разрешения. Это мгновенно обрушило частоту обновлений нашего приложения. Стало понятно, что в Continuous Integration нужно добавить проверку, которая сигнализировала бы об изменениях в списке разрешений. К сожалению, готовых решений в тот момент не существовало. Первое, что пришло в голову — написать юнит-тест, который программно все это проверит, но написать такой тест не вышло (нельзя получить все разрешения). Вторая попытка — распарсить AndroidManifest.xml
, и, конечно, эта затея тоже была обречена на провал, поскольку разрешения сторонних библиотек лежат в их собственных манифестах и управляются сборщиком манифестов. Наконец, я решил проанализировать сгенерированный APK, вытащить из него полный список разрешений и потом сравнить с предыдущими, заранее сохраненными, результатами (https://github.com/thyrlian/NoNewPermissionForAndroid). Этот подход сработал отлично, но, как видите, он не является интуитивно-понятным и требует дополнительной работы. Кстати, начиная с Android Studio 3.0, встроенный APK Analyzer предоставляет аналогичную функциональность из коробки (https://developer.android.com/studio/build/apk-analyzer.html). Экосистема становится все лучше и лучше.
— В России существует культура высокоспециализированных команд: отдельная разработка, отдельное тестирование и т.п. Расскажи, каким инструментам стоит научиться сисадмину, чтобы лучше взаимодействовать с мобильными разработчиками, помогать им более эффективно?
— Мобильным разработчикам сисадмины кажутся волшебниками. По опыту моих предыдущих работ, хороший волшебник в мобильной команде выглядит так:
- Он не просто мастер консоли, он еще и хорошо разбирается в проекте. Например, Gradle де-факто является официальным инструментом сборки для Android, поэтому разумно выбрать Groovy как основной язык для всех скриптов сборки. А вот на iOS очень популярны CocoaPods и Fastlane, поэтому выбрать стоит уже Ruby.
- Сисадмины не смогут охранять покой команды 24/7. Члены команды самостоятельно должны понимать, как пробиться сквозь типичные проблемы сборки, особенно сквозь мелкие, но неотложные проблемы. Когда не нужно постоянно ждать кого-то, кто придет и решит твою проблему — растет не только эффективность, но и твоя удовлетворенность работой.
- «Мобильные разработчики» называются «мобильными разработчиками», потому что хорошо разбираются в мобилках. Им не обязательно хорошо разбираться в базах данных или чем-то еще — по факту, они обычно и не разбираются. Но как только мобильное приложение начинает общаться с сервером по API, при возникновении проблем нужно все это отлаживать, и для мобильного разработчика эта отладка — большая боль. Даже не пытайтесь учить их сложным SQL-запросам или как погрепать логи огромной командой в консоли. Лучше устроить для них небольшой ознакомительный курс по использованию Kibana или Grafana, в которые вы самостоятельно вбили часто используемые запросы.
- С другой стороны, админ должен четко знать потребности мобильного разработчика и понимать цель, которую он хочет достичь. Может быть, вы уже тысячи раз настраивали правила Sonar для Java-бэкенда, но эти стандартные правила не подходят для Android. Android-разработчикам нужны свои специальные настройки. Перед тем, как отдавать им готовое решение, внимательно проверьте, что это решение специально заточено для мобильной разработки.
— Какие технологии должен изучить разработчик, чтобы выстраивать хорошую инфраструктуру и правильный DevOps-процесс? Как писать мобильные приложения так, чтобы их было удобней девопсить?
— Нужно изучить хотя бы один скриптовый язык, потому что в типичной среде сборки нельзя рассчитывать исключительно на Java/Objective-C. Функциональность по сборке нужно превращать в модули, небольшие фрагменты, которые не просто упрощают рефакторинг, но и позволяют проще адаптироваться к различным условиям (например, при переходе с пайплайнов Jenkins на Cricle CI, или если с Circle CI нужно перепрыгнуть на Travis CI). Мобильная разработка стремительно эволюционирует, поэтому не стоит закладываться на использование исключительно каких-то конкретных сторонних решений, ведь они могут стать устаревшими в любую секунду. Закладывайтесь на официальные инструменты и публичные API от Apple и Google, и созданные на их основе инструменты. И главное, думайте широко, рассматривайте решения, отличающиеся от своей текущей конфигурации. Например, если Android-разработчик вдруг захочет установить на вашу среду сборки (например, на MacMini) какой-то новый инструментарий, попробуйте проанализировать, к каким последствиям это приведет.
— ОК, спасибо! Встретимся на Mobius 2017!
Автор: Олег Чирухин