Вы идёте в ногу со временем, и ваше веб-приложение использует самые передовые технологии? Тогда вы совершенно точно используете микрофронтенды! Достаточно провокационно, правда?

Все эти сложности и трудности, но ради чего? Ваш фронтенд в любом случае устареет через пару месяцев, и вам лучше инвестировать в переиспользуемые компоненты. Ничто не сравнится с монолитом! Тоже довольно узкая точка зрения, верно?

С большой вероятностью вы согласились с первым или вторым параграфом. Однако, как это всегда бывает в разработке программного обеспечения, ответ находится где-то посередине:

Все зависит от ситуации!

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

Чтобы получить реальное представление о том, как составлять фронтенд приложения с использованием независимых компонентов, прочитайте эту статью Джонатана Саринга (Jonathan Saring).

Она рассказывает историю Bit.dev, как они прошли множество испытаний и добились успеха в построении их собственного фронтенд-приложения с использованием микрофронтендов, которые интегрируются во время сборки (делают они это, используя собственный продукт – Bit).

Причины использовать Монолит

Многие люди утверждают, что выбор между монолитом и микрофронтендами следует принимать в зависимости от размера приложения. Я считаю, что это не совсем так. Конечно, если приложение на самом деле маленькое, то монолитная архитектура потенциально уменьшает время на переписывание приложения до состояния, когда всё выглядит дорогим и раздутым. Однако для меня реальным показателем служит перспектива для бизнеса.

Если приложение должно быть довольно статичным, не так часто обновляться и оснащаться функциями, которые должны быть доступны всем, то монолит – отличный выбор.

Монолит легко разрабатывать, легко развёртывать и легко тестировать, по крайней мере, когда монолит небольшой. Это, конечно, не заслуга монолита: любую систему легко понять, когда она маленькая и посвящена решению одной задачи.

Коротко:

  • консистентность

  • надёжность

  • производительность

Причины использовать Микрофронтенды

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

Вещь, которую опасаются большие приложения - "legacy". Наличие унаследованного кода или неспособность использовать новейшие и лучшие инструменты ведёт к провалу проекта. Это происходит либо из-за пропуска критических обновлений, либо из-за неспособности привлечь новых разработчиков. Микрофронтенды предоставляют хороший выход из этой ситуации, позволяя фрагментам отличаться друг от друга, в зависимости от основных технических решений.

При правильной постановке задачи микрофронтенды могут превзойти своих монолитных предков
При правильной постановке задачи микрофронтенды могут превзойти своих монолитных предков

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

Кратко:

  • масштабируемость

  • гибкость

  • независимость

Согласования и Совместная работа

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

В зависимости от структуры приложения на микрофронтендах может быть одна центральная команда, отвечающая за сквозные проблемы и управление. Остальные команды можно считать вспомогательными. В каждой из них от 1 до 5 разработчиков, в зависимости от объёма функций. Согласования между командами почти не требуется - даже при том, что желательна некоторая согласованность с владельцами бизнеса или центральной командой. Каждая вспомогательная команда может работать над их собственным расписанием и делать релизы, когда они к этому готовы.

Разные команды занимаются разными частями приложения
Разные команды занимаются разными частями приложения

В отличие от микрофронтендов, монолит состоит либо из одной команды, либо из большой центральной команды и нескольких маленьких, которые занимаются отдельными функциями приложения. Однако, в любом случае, будет происходить согласование между командами. Есть сценарий, в котором дополнительные команды также достаточно большие и работают самостоятельно. Вот тут-то и появляются такие понятия, как "nexus" и "scrum of scrums". Как только мы слышим эти термины, мы понимаем, что это много согласований, много митингов и большая потеря эффективности.

Одна большая команда, создающая одно приложение
Одна большая команда, создающая одно приложение

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

Развёртывание

Одним из наиболее важных вопросов для любого проекта является способ развёртывания. Я видел проекты на микрофронтендах, которые развёртывали полностью в одно время. Каждый микрофронтенд выходил в релиз в одном большом CI/CD пайплайне. Я определённо против такой модели.

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

Что мы теряем, делая совмещённый релиз?

  • Независимость (команды должны работать совместно, заниматься подготовкой к этому и т.д.)

  • Кэширование (все ресурсы инвалидируются в одно время, вместо того, чтобы инвалидировать каждый ресурс только в тот момент, когда он поменяется)

  • Скорость (нам нужно согласовать дату публикации, что означает дополнительную потерю эффективности)

Что мы получаем, делая совмещённый релиз?

  • Согласованность (мы знаем, что все части обновлены до последних версий)

  • Надёжность (мы можем провести всего один дымовой тест, чтобы убедиться, что всё в порядке)

  • Ознакомленность (вместо постоянных изменений, приложение будет обновляться только через определенные промежутки времени)

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

Микрофронтенды могут быть также развёрнуты группами. Например, у нас может быть несколько "основных" микрофронтендов, разработанных одной или несколькими командами. Эти основные микрофронтенды могли бы развёртываться совместно. Такой смешанный подход может быть хорошим компромиссом, направленным на то, чтобы избежать потерю скорости, независимости и возможности кэширования, сохраняя при этом согласованность, надёжность и ознакомленность. Это система, которая уже достаточно хорошо известна по мобильным операционным системам (или вообще по большинству операционных систем):

  • сторонние приложения находятся в собственном цикле релизов

  • некоторые основные приложения могут обновляться независимо

  • с новым релизом ОС также поставляются новые версии основных приложений

В некотором смысле полностью работающее решение на микрофронтендах можно рассматривать как мобильное приложение. Возможность настройки стратегии развёртывания - одно из преимуществ микрофронтендов.

Заключение

Выбор между монолитом и микрофронтендами не должен быть сложным. Обычно, не особо задумываясь, мы можем начать с монолита. Решение о переходе на микрофронтенды всё ещё можно будет сделать, когда это потребуется.

Тем не менее, оба типа проектов имеют свои преимущества и недостатки. Мы всегда должны пытаться найти золотую середину, которая решает нашу задачу наилучшим образом. Если это монолит - отлично! Если мы придём к микрофронтендам - тоже отлично!

Не беспокойтесь о людях, рассказывающих вам, что современно, а что является лучшей практикой. Лучше подумайте о вашей проблеме и постарайтесь найти лучшее решение. Это также больше, чем просто техническая и бизнес перспектива - не следует пренебрегать своей командой (учитывайте опыт каждого, насколько они открыты для различных решений и т.д.).