SDCast #37: в гостях Евгений Кривошеев, инженер, спикер, agile тренер

sd-podcast-logo Друзья! Рад представить вам 37-й выпуск SDCast’а! У меня в гостях Евгений Кривошеев, инженер, спикер на многих конференциях, agile-тренер и консультант. В этом выпуске речь идет не о каком-то конкретном продукте или проекте, а в большей степени затрагивает концептуальные и методологические аспекты разработки и проектирования информационных систем в целом.

Мы обсудили различные методологии и практики, используемые в процессе разработки, среди которых такие популярные методологии, как agile, scrum и kanban, так и менее известные, как Cynefin. Женя рассказал про некоторые особенности и отличия, о том, как эти методологии вписываются в корпоративную культуру компаний, как их можно внедрять в уже сложившиеся команды и как начать применять на ранних этапах формирования проектных команд, на что следует обратить внимание и какие аспекты наиболее критичны.

Так же, обсудили тему построения архитектуры проекта в современных быстро изменяющихся условиях, зачем нужен devops и почему так важно с самого начала выстраивать процессы continious integration (CI) и continious delivery (CD), насколько важны тесты и максимальная автоматизация всех процессов.

В завершение беседы, немного порассуждали о том, как может развиваться ИТ-индустрия в целом в ближайшем будущем, какие новые процессы и тенденции появляются и куда вообще катится айтишный мир :)

Ссылки на ресурсы по темам выпуска:

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

Скачать (mp3, 32 MB) Скачать (ogg, 33 MB)
  • Deema Lee

    Константин, что с RadioJS?
    Ждем разработчиков в ваших подкастах. Т.к. последние 2: сито – вода – песок – лопата. Одним словом, тупик…

  • Анатолий Северин

    Интересно, но мало.

  • Спасибо за выпуск, узнал много нового.

    Я так понимаю, что идеальным кирпичиком agile должны стать микросервисы? Малые структурные взаимозаменяемые единицы.

    PS Надо рассказать руководству про “зелёные пятницы” :-)

  • Спасибо за выпуск, много прояснилось. По мотивам вашего обсуждения сибимбоза молодых и старых программистов я написал статью
    http://dou.ua/lenta/articles/why-need-junior/

  • Maxim Kolesnikov

    Прекрасный подкаст получился. Но таки да, маловато.

  • B7W

    Клевый подкаст, спасибо з труд

  • Виталий Исаев

    Константин, большое спасибо за столь интересного собеседника!

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

    Если Вы вдруг читаете эти комментарии, пожалуйста, поясните, что Вы имеете в виду под заказной (“олдскульной”) и продуктовой (“хипстерской”) разработкой. В чем всё-таки причины отличия качества кода у разработчиков, относящихся к этим группам?

    • Пожалуйста! :)
      Я передам Жене ваши слова ;)

    • Виталий, Евгений сейчас в отпуске с плохим инетом, поэтому вставляю его ответ, присланный мне по почте :)

      =====================================

      Привет ))

      Нет, боюсь я был немного неверно услышан ))

      Оси выбора “олдскул”–“хипсторы” и “заказ”–“продукт” – это разные выборы и разные модели бизнеса и проектирования. Но да, часто наблюдается корреляция: продуктовая бизнес-модель и культура часто тяготеют к хипстор-стайл ))) И наоборот, заказная разработка чаще использует олд-скул модель проектирования. Хотя в последнее время мы видим большее смешение и взаимопроникновение.

      В чем разница? Олд-скул модель проектирования и разработки – это подход с ярко выраженным BDUF (big design up-front): когда мы пытаемся сначала увидеть общую картину и запроектировать решение, учитывая все особенности задачи и ее потенциал ее изменчивости. То есть в нашем дизайне сразу появится функционал, будет заложена гибкость для возможных вариантов его изменчивости, будут сразу реализованы нефункциональные требования (производительность, надежность, etc), причем часто с запасом (большим!). “Семь раз отмерь – один раз отрежь” и вот это все. Выглядит вроде клево, и нас так долго учили делать. Но есть очень серьезные проблемы с таким подходом: мы выгребаем сразу два вида неопределенности.

      Первая – внешняя неопределенность, т.е. неопределенность требований. Мы _не знаем_ как будет меняться функционал и нефункциональные требования. И в попытке забороть эту неопределенность, мы делаем “с запасом”. Запас по гибкости функционала, запас по производительности, надежности и т.д. Но запас – штука очень дорогая. Дорогая сегодня в реализации и еще дороже завтра в сопровождении, т.к. если этот запас не пригодится, тащить эту сложность с собой в любом случае придется.

      Вторая неопредленность – внутренняя. Мы _не знаем_ заранее, как будет выглядеть решение. И тешим себя иллюзией, что быстро заборем. Но в реальности придется проглотить _очень_ много сложности за один раз. Задача (функционал) обычно сама по себе непростая, плюс предметка непростая, плюс нефункциональные требования фиг поймешь, как реализовать, плюс мы еще накручиваем сложности ради “запаса”. В итоге часто мы попадаем в ловушку т.н. “аналитического паралича” – когда тянем за разные ниточки решения, но на нас падает бетонный блок сложности, мы пробуем другую ниточку с тем же результатом, и так до тех пор, пока горько не заплачем ))) То есть мы с самого начала ошиблись с классификацией задачи – думали, что она на реализацию (когда сразу ясно, как делать), но она на исследование (когда неясно вначале, как делать и нужно (не)много поэкспериментировать, чтобы нащупать подходящее решение). Гордыня и неумение классифицировать задачи по степени неопределенности – нашей способности _действительно_ знать готовое решение или быстро его сверстать.

      В итоге как в реальности часто выглядит BDUF: вначале проекта мы долго и клево проектируем, получается очень “красивый” дизайн, мы очень довольны собой. Но по мере столкновения с реальностью выясняется, что требования немного другие, меняются не так, как ожидали. Да и дизайн наш не очень мягко реализуется – абстракции протекают, выясняется, что мы многого не учли, а где-то зря сильно перезаложились. В итоге ближе к сдаче проекта наш красивый дизайн обрастает костылями, мы начинаем сильно спешить, и он нам все больше мешает. К финишу приползает уродец, где местами просвечивают первоначальные задумки.

      Хипста-стайл (он же emergent design, YANGI, KISS) другой. Мы изначально принимаем, что мы ничего не знаем – ни задачу, ни решение. Поэтому у нас остается единственный способ – пробовать. Как _через действие_ уточнять задачу, так и наше решение. “Фигак-фигак и в продакшн” и вот это все. То есть мы в каждым момент времени делаем максимально _просто_ и забарываем задачи _по одной_. Не пытаясь построить общее видение решения во всех деталях – у нас не хватает думалки, чтобы сразу учесть все возможные детали.

      (Кстати, привет фреймворку cynefin – смотрите, как половинки матрицы по-разному дают нам ответы на разные уровни неопределенности – “пробуй” и “думай”).

      Так что в этом mindset мы наслаиваем функциональные и нефункциональные требования как тонкие слои масла на бутерброд – один за другим. Это позволяет _продвигаться_, а не адово рефлексировать в аналитическом параличе и тащить с собой минимум сложности.

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

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

      Но чтобы верно выбрать подход, в первую очередь нужно понимать, в какой неопределенности вы находитесь. Честно и объективно, а не наши влажные фантазии. Для внешней неопределенности: _често_ ответьте себе на вопросы “сколько у меня есть времени на задачу, перед тем, как она успеет протухнуть – измениться или удалиться” и “на сколько времени вперед мы можем планировать задачи и они _действительно_ не изменятся за это время”. И для внутренней неопределенности – что вы испытываете при фразах “надо быстренько поправить”, “тут тестировщики бажик прислали, говорят, несложный”, “да задача легкотня”, “давайте сейчас быстренько учтем все требования и запилим красивый дизайн”, гундосым голосом: “нет, я не согласен с дизайном, мы не учли требование №666, надо все перепроектировать”. Если захотелось плакать или кого-то ударить – значит, для большинства задач вы не можете быстро запроектировать дизайн, который не изменится в процессе его реализации. Это не плохо, просто надо переходить к другому процессу и пилить задачи по одной и _просто_.

      • Виталий Исаев

        Спасибо! Очень интересная точка зрения; многое прояснила.

  • Vadim

    Да, офигенное получилось обсуждение. Спасибо.
    Константин, пригласите, пжл, Гайдара Магданурова, я думаю, что его в качестве гостя будет многим интересно послушать.

    P.S. спасибо, Евгению, его всегда интересно послушать

  • Nikolay Podol

    Отличный подкаст, актуальные вопросы, интересная штука
    Еще хотелка есть на взаимодействие в комманде:
    1) стоит ли разделять cостав команды(разработчиков отдельно от аналитиков и QA)
    2) как способствовать улучшению взаимодествия между участниками команды когда они конфликтуют по дефолту
    3) поделиться опытом практик похожих на проведение командой анализа какого-то объема работы, где определяют допущенные ошибки и находят их решения

    Хотя 2 – это больше зависит от людей и нужно смотреть кого нанимаешь, а 3 – это ретроспектива и нужно проводить ВСЕГДА КОГДА ЕСТЬ В НЕЙ НЕОБХОДИМОСТЬ
    В общем заказ на подкаст командного взаимодействия))

    • О! Вот это правильные вопросы, удивительно, почему я не задавал их раньше %) Добавлю в копилку своих обычных вопросов ;) Спасиб!