Pull to refresh

Главное — хвост. Технология конвейеризации разработки программного обеспечения

Reading time10 min
Views8.6K

Написано в сотрудничестве с Ревазом Бухрадзе (редактор: Ангелина Кипелова)


Технология тем и отличается от кустарного производства, что результаты повторимы, а сроки их достижения прогнозируемы, также и в любой науке результаты эксперимента признаются только в случае, если их удалось повторить (а еще лучше – поставить на поток). И её смысл заключается в том, чтобы успешно воспроизводить алгоритм работы каждый раз, когда это нужно. Например (это как раз плохой пример) китайские типографии печатают каталоги и упаковки дешево, но за ними нужен глаз да глаз. Сегодня они использовали выданные заказчиком настройки, а завтра решили, что они знают, какие подешевле лучше цвета использовать. И, скажем, вместо черно-желтых полосок Билайн может обрести красно-синий колер. А восточная бригада рабочих, оставленная без присмотра в процессе кладки кирпичной стены, может изобразить инсталляцию «бегущая волна» при помощи подручных стройматериалов. То есть, смысл технологичности в том, чтобы система работала автономно, и результат на выходе каждый раз был одинаково удачным. Ну за редким неизбежным исключением.


Философский камень универсальной методологии


Специалисты спорят до кровавых холиваров, какая модель производства ПО лучше, и когда (какую и для чего) методологию стоит применять в крупных компаниях. Там, где уследить за департаментом разработки невозможно физически, и где любые задержки и критические ошибки чувствительно отражаются на работе гигантской махины. Очень хочется каждому солдату стать генералом специалисту нащупав тот самый «универсальный» метод, который позволит сократить количество проблем в процессе разработки, при этом повысить эффективность до уровня «утритесь, конкуренты!» (однако, как известно — нет серебряных пуль).


Однако если не определить, что значит это самое «лучшее решение» в каждом определенном случае, то найденные ответы будут похожи на мебель из Икеи: «вот общие рецепты, а дальше все сами». Так же, как и лекарство подбирается индивидуально под ряд параметров (хотя результат стремления везде одинаков – выздоровление), так и методология разработки ПО тоже подразумевает предварительный анализ поля «дано».


Применение различных моделей разработки ПО: когда и что срабатывает лучше


  • Водопадная модель эффективна, если хорошо определены требования, и за время проекта они сильно меняться не будут. Заказчик не прибежит, помахивая свежим ТЗ, и не плюхнет его на стол с громким заявлением: «Концепция поменялась!». Если срок исполнения не полыхает, а ресурсов хорошей квалификации достаточно для реализации проекта – модель неоспоримо прекрасна.


  • Итеративная — подойдет в том случае, если ожидать изменения концепции все-таки стоит. Но не факт, что заказчик решится на кардинальные меры. При достаточно стабильной концепции-скелете возможна модификация деталей проекта. В такой модели допускается возможность реализация конечного результата «по частям». При этом очень важно, чтобы ресурсы обладали не просто хорошей квалификацией, но и имели широкий профиль, адаптирующийся к изменению требований.


  • Agile – модель, лояльная к отсутствию определенных требований в начале проекта. Выглядит примерно как «Боря! Жарь рыбу!» «Да где та рыба, Степа?» «Боря, ты пока начинай, а рыба будет!». То есть, если требования расплывчаты, и будут появляться, изменяться и переворачиваться с ног на голову.
    Эта модель позволяет реализовывать конечный результат «по частям» с максимально ранним получением работающего продукта, реализующего основной замысел. Требование к этой модели — достаточное количество ресурсов хорошей квалификации, причем существенная часть — широкого профиля. Адаптация к изменению требований должна быть моментальной.

Есть и другие методологии [1],[2] но приведенные выше считаются основными и достаточно широко используются на практике.


Почему именно так?


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


  • уровень неопределенности и риски связанные с ошибками на ранних стадиях процесса (сбор и анализ требований, проектирование);
  • наличие и компетентность персонала;
  • время до получения готового результата.

При этом почему, казалось бы, неэффективная водопадная модель, очень жестко ограничивающая вариацию требований, жива, здравствует и активно используется на практике? Помимо борьбы с неопределенностью не менее важным фактором выступает….


Экономика производства


Если стоит задача минимизировать расходы на производство, то водопадная модель (при своих условиях) демонстрирует уверенную рабочую эффективность. Впрочем, ключевым словом здесь является «условие». Поэтому для каждой представленной выше методологи следует рассмотреть схему процессов и затрат на них.


Процесс Расходы связанные с объемом задачи Расходы связанные с длиной производственного цикла
Анализ и проектирование (АП) Разработка требований и архитектуры Поддержание документации в целостности
Разработка и документирование (РД) Разработка, проверка кода и документации и исправление ошибок найденных на этапе тестирования Сборка и поддержание целостности документации
Тестирование (Т) Функциональное и интеграционное тестирование Регрессионное и нагрузочное тестирование
Внедрение (В) Сборка, управление дистрибутивами и конфигурациями, развертывание
Администрирование Планирование и управление ресурсами (в случае agile-ритуалы )
Управление производственными средами (Dev|Test|Prom), поддержка инструментария и процессов Dev и Ops и т.п.

Проведем качественное сравнение экономики процессов для водопадной модели и agile, взяв за $X$ — трудозатраты, необходимые для реализации заданного объема функционала, а за $C$ — трудозатраты, связанные с производственным циклом. В этом случае общие трудозатраты составят:


  • для водопадной модели $(1+p)\cdot (X + C)$, здесь $p$ — коэффициент, связанный с объемом доработок, возникающих вследствие изменения исходных требований;
  • для agile — $(1+p)\cdot X + N\cdot C$, где $N$ — количество итераций, необходимых для достижения результата.

Сравнивая эти результаты, мы получаем следующий вывод:


  • водопадная модель эффективнее agile в случае, если $(1+p) < N$ т. е. объем переработок невелик.
  • при высокой степени неопределенности и высоком риске доработок $(1+p)\ge N$ agile становится эффективнее.

Также можно заметить, что автоматизация процессов производства (или модный DevOps) существенно повышает экономическую эффективность agile за счет минимизации расходов (связанных с длиной производственного цикла), т. к. этими производственными расходами $C$управлять куда проще, чем желаниями и фантазиями заказчика $p$.


Стоит подчеркнуть, что приведенные выше рассуждения качественные, а не количественные. Поэтому в каждом конкретном случае необходимо делать расчет, основываясь на текущем распределении ролей производственных сотрудников в компании.


Экономический аспект на этом можно считать закрытым, критерии выбора достаточно объективными. Теперь переходим к следующему вопросу.


Ресурсная загрузка


На этом в свое время погорела плановая экономика, когда один и тот же результат нужно было получить при разных условиях труда. Например, астраханцу и эскимосу поручено вырастить тонну арбузов. Вынь и выложи – к августу должны быть! Первому достаточно просто взять в руки двустволку, заряженную солью, и гонять с бахчи охотников за дармовщинкой. А второму придется придумать и оборудовать высокотехнологичную систему микроклимата.


Вопрос ресурсной загрузки лучше всего рассматривать на примере профилей участников упомянутых выше процессов. Для исследования будем использовать итеративный подход RUP, и увидим неравномерности загрузки (картинка с wikipedia).


image


Эти неравномерности требуют от менеджмента плясок с бубнами заметных усилий для соблюдения сроков сдачи проекта. Необходимо минимизировать простои и назвать клиентам реальные сроки исполнения задач. Причем для водопадной модели и для agile (в части спринта), ввиду, того, что этапы внутри соответствующих производственных циклов организованы последовательно, данная проблема с неравномерностью использования стоит острее, чем для моделей итеративного типа. Почему острее, — построим профиль ролей для, например, для waterfall — цикла разработки в 10 недель.


image


Теперь предположим, что у нас на подходе есть следующая аналогичная по размерам и сложности задача и нам надо спланировать её оптимальное выполнение. Если не заниматься дефрагментацией загрузки, или как часто шутят «тетрисом», то получится следующая картина, позволяющая при 10-недельном производственном цикле выпускать готовый продукт раз в 7 недель (разрыв между релизами помечен красной стрелкой <=>):


image


которая ввиду наличия «серой зоны» и её достаточно большого размера, очевидно, не является оптимальным решением для обеспечения равномерной загрузки персонала.


Теперь обратите внимание на серую зону – она достаточно велика, чтобы сделать понятный вывод: расчет не оптимален. Нет здесь равномерной загрузки персонала. Однако после некоторой оптимизации и перепланировки картину можно несколько улучшить: сократить общую длительность проектов на две недели, оптимизировать загрузку персонала, что при таком же 10-недельном цикле позволит выпускать готовый продукт уже раз в 5 недель:


image


Проблема конвейера – точно вовремя


Это только на бумаге получается идеально оптимизировать работу. А де-факто на время планового простоя персонала бывает довольно сложно придумать, чем бы занять ресурсы. В теории – дать полезную загрузку, на соответствующие периоды отдав их, например, в другие проекты. Но для этого нужны проекты, которые реализуются в «кусочках». Что в реальности, скорее, утопия, чем реальная возможность. Большинство проектов требуется сделать «от и до». Поэтому в полноценных периодах, позволяющих добиться результата, зияют дыры, и менеджменту приходится снова и снова заниматься перепланированием. Создавать авралы, периоды переработки и закономерных простоев. Та же проблема, только в меньшем объеме характерна и для итеративного подхода, — достаточно в качестве единицы измерения взять не неделю, а 2-3 рабочих дня.


Отдельно стоит отметить и то, что это проблема характерна и для agile методологии, причем ввиду краткой длительности спринта (обычно две недели) она еще усугубляется. Чтобы решить сложную задачу, требующую существенной трудоемкости, нужно выйти за пределы трудомощности одного спринта. Следовательно, появляется тот самый «аврал»: увеличивается нагрузка на аналитиков и архитекторов в части разбиения задачи на подзадачи и поддержания целостности результата каждого спринта.


Сформулируем, чего мы хотим от идеального процесса реализации проекта, и каким критериям он должен удовлетворять:


  1. иметь разумные затраты на администрирование;
  2. поддерживать высокую степень определенности требований, давая при этом заказчику остаточную свободу фантазии;
  3. обеспечивать существенную трудомощность на каждый производственный цикл, позволяя решать сложные задачи за один этап;
  4. гарантировать регулярный выпуск продукта для того, чтобы иметь возможность оплачивать труд команды;
  5. обеспечивать непрерывную и равномерную загрузку команды.

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


Причем здесь Kanban?


Знаменитая японская методология используется не только на заводе по производству автомобилей Toyota. Если применить ее в итеративной разработке, она позволяет при помощи задаваемых ограничений на «работу в производстве» (WIP – work in progress) создать аналог избыточных запасов в производственной модели и синхронизировать относительные объемы работ, выполняемых на различных этапах производственного цикла. Таким образом, минимизируется незавершенное производство. При этом процесс достаточно экономен, в то время как трудомощность на цикл позволительно увеличить. Однако критерии регулярного выпуска и гарантированной загрузки по умолчанию не выполняются.


Чтобы обеспечить их выполнение, необходимо сравнить производственные циклы сборки машин и производства ПО (картинки найдены в интернете).


Конвейер Toyota Офис разработки

Чувствуете разницу?


А она есть в том, что на конвейере процессы построены так, что длительность каждой операции примерно одинакова. Алгоритм известен, отработан и автоматизирован. Поэтому и не возникает простоев или накопления движущихся по конвейеру деталей. Более того, конвейер проектируется так чтобы двигаться равномерно и непрерывно.


Тем не менее, систему kanban можно примерить в производстве ПО, если сделать то же самое, настроить конвейер. То есть, определить длительности этапов производственного цикла и стараться выдерживать их.


Длительность производственного цикла возьмем, равную $16$ неделям, при этом готовый продукт будет появляться раз в $4$ недели, что позволит постепенно «догнать и обогнать» классическую итеративную модель, а именно, если сравнивать длительность производственных циклов в неделях, мы получим $10+5x=16+4x$ откуда получаем $x=6$, т.е. на седьмом производственном цикле мы уже будем получать эффект.


image


Данный подход по построению обеспечивает равномерную загрузку всех задействованных ресурсов, однако для того, чтобы перейти к нему, стоит принять во внимание важную тонкость. Она связана с численностью задействованного персонала, необходимого для обеспечения непрерывности и равномерности процесса.


Численность на каждом из этапов должна соответствовать объему работ, поступающих с предыдущего этапа. То есть, все, что пришло, должно быть переработано вовремя, а то, что не получилось освоить будет перенесено на следующий производственный цикл. Поэтому, чтобы перейти от водопадной или классической итеративной разработки к инновационной системе, необходимо будет перебалансировать существующую численность между этапами.


Для этого сначала введем единицу измерения доступной трудуомощности – пусть это будет «квадратик» или кв. Данная единица соответствует объему, который может сделать команда из $n$ человек в течение недели. Тогда балансировка должна проводиться следующим образом:


  • Аналитики и проектировщики — объем доступной трудомощности в итеративной разработке 10 кв., объем эффективной трудомощности 4 кв. соответственно при длине производственного такта в 4 недели необходимо 4 кв. Количество аналитиков и архитекторов, которых надо переориентировать на другие работы, составляет 60% от текущей численности;
  • Разработчики и технические писатели — как при итеративной разработке, так и при конвейерной — по 12 кв., и вся трудомощность эффективная — перебалансировка не требуется;
  • Тестировщики — при итеративной разработка трудомощность 10кв., при эффективной — 7 кв.; при конвейерной — 8 кв. То есть, переориентировать на другие проекты необходимо 20% от текущей численности по роли;
  • Внедренцы — объем доступной трудомощности в итеративной разработке 10 кв., объем эффективной трудомощности 3 кв., при конвейерной разработке — 4 кв., т. е. количество внедренцев, которых надо переориентировать на другие работы, составляет 70% от текущей численности.

Однако данный подход, как и все в ИТ, не является «серебряной пулей», наповал убивающей монстра сорванных сроков. Да, методология позволяет неплохо решать вопросы, связанные с оптимизацией ресурсного планирования, но по задачам необходимо учитывать риски, напрямую следующие из правил построения конвейера:


  • На этапах анализа и проектирования необходимо учитывать трудомощность, доступную на всех последующих этапах;
  • При конвейерной схеме есть только минимальные возможности для доделок, и доработок и прочих работ по «занесению хвостов». Все то, что не проходит соответствующий этап, вовремя должно быть снято с конвейера, как брак. И эти показатели необходимо учитывать в объеме доработок на следующем такте. В противном случае конвейер рассинхронизируется и тут же потеряет эффективность (а с ней и смысл);
  • Конвейер по своей природе, обеспечивая высокую эффективность, является в некотором смысле потогонной машиной;
  • В отличие от «веселого» подхода aglile, стимулирующего расширение компетенций по всем направлениям команды для обеспечения взаимозаменяемости, конвейер направлен на углубление компетенций и повышение персональных навыков в своей и смежной областях. То есть, разработчик должен более или менее разбираться в архитектуре, чтобы даже и не начинать кодирование по спецификации, которую он считает некачественной.

Учет этих рисков требует более жесткого планирования на начальном этапе и должной смелости в принятии решений об отказе от доработок в последний момент, когда это сделать очень хочется, а сроки, как обычно, поджимают.


Выводы


В общем, прав был дедушка Форд, когда от заказной разработки перешел к конвейерному производству автомобилей, что потом вслед за ним проделали все другие крупные автопроизводители и они — капиталисты не спорили о методе, а использовали то, что эффективнее (хотя надо отметить, что болиды F1 собираются по технологии с элементами agile). Учитывая почти вековой опыт конвейерного производства, однозначно стоит использовать алгоритмы высокотехнологичной отрасли на благо будущих результатов.

Tags:
Hubs:
+6
Comments7

Articles