Статьи

Клиент-серверная архитектура и микросервисы: в чем разница и как они работают вместе

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

При этом клиент-серверную и микросервисную архитектуры неправильно воспринимать как альтернативы. Они описывают разные уровни системы: первая — взаимодействие клиента с сервером, вторая — устройство серверной части.

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

Клиент-серверная архитектура

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

Упрощенно взаимодействие выглядит так:

Клиент → HTTP-запрос → Сервер → обработка → HTTP-ответ → Клиент

Например, пользователь открывает страницу интернет-магазина. Frontend отправляет запрос GET /products, сервер получает данные о товарах и возвращает их клиенту. Пользователь при этом не знает, где именно хранятся данные и какие операции сервер выполнил перед формированием ответа.

Главная идея такой архитектуры — разделение ответственности. Клиент отвечает за взаимодействие с пользователем и представление данных, сервер — за бизнес-логику, работу с данными и предоставление API.
При этом клиент-серверная архитектура ничего не говорит о том, что происходит внутри сервера. Сервер может быть одним приложением, несколькими сервисами или вообще представлять собой сложную распределенную систему.

Монолит: один сервер — одно приложение

Один из вариантов реализации серверной части — монолит. В этом случае бизнес-логика приложения находится в одном разворачиваемом приложении.

Для интернет-магазина это может быть Java-приложение, внутри которого есть модули пользователей, каталога, корзины, заказов и платежей:

Frontend → Java-приложение → база данных

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

Проблемы обычно появляются с ростом системы. Если приложение становится большим, его сложнее изменять и тестировать. Разные команды начинают конфликтовать за одни и те же части кодовой базы, а отдельное масштабирование компонентов становится невозможным.
Например, если каталог получает в десять раз больше запросов, чем оформление заказов, при обычном монолите нельзя независимо масштабировать только каталог, придется масштабировать все приложение.

Именно здесь микросервисная архитектура может стать одним из вариантов решения.

Что такое микросервисная архитектура

В микросервисной архитектуре приложение состоит из нескольких автономных сервисов, каждый из которых отвечает за определенную бизнес-функцию.

Тот же интернет-магазин можно разделить на сервисы:

Frontend → API Gateway → Catalog Service

** ↘ Order Service**

** ↘ User Service**

** ↘ Payment Service**

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

Например, сервис заказов отвечает за создание и изменение заказов, а сервис пользователей — за учетные записи и связанные с ними операции. Сервис заказов не должен напрямую менять таблицы сервиса пользователей только потому, что обе части системы используют одну СУБД.

Как микросервисы взаимодействуют

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

  • Для синхронного взаимодействия часто используют HTTP/REST или gRPC. Например, Order Service может запросить у Catalog Service информацию о товаре.

  • Другой вариант — асинхронное взаимодействие через брокер сообщений. После создания заказа сервис заказов может опубликовать событие OrderCreated. Его обработают другие сервисы: например, сервис уведомлений отправит сообщение пользователю, а аналитический сервис сохранит событие для дальнейшего анализа.

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

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

Что происходит с базами данных

В монолите несколько модулей могут работать с одной базой:

Application → Database

В микросервисной архитектуре обычно стремятся к принципу database per service: каждый сервис является владельцем своих данных, а другие сервисы получают необходимую информацию через API или события.

Например:

Order Service → Orders DB

User Service → Users DB

Catalog Service → Catalog DB

Это позволяет сервисам быть более независимыми, но усложняет работу с данными.

Допустим, оформление заказа требует информации о пользователе, товаре и оплате. В монолите подобная операция может выполняться в рамках одной базы и одной транзакции. В микросервисной системе данные распределены между несколькими владельцами.
Поэтому приходится учитывать распределенные транзакции и eventual consistency — ситуацию, когда разные части системы могут прийти к согласованному состоянию не одновременно.

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

Зачем нужен API Gateway

Если frontend взаимодействует непосредственно с каждым микросервисом, клиенту придется знать внутреннюю структуру системы:

Frontend → Catalog Service

Frontend → Order Service

Frontend → User Service

Frontend → Payment Service

Это создает дополнительную связанность. Поэтому между клиентом и сервисами часто размещают API Gateway.

Теперь клиент взаимодействует с единой точкой входа:

Frontend → API Gateway → Microservices

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

Масштабирование: одно из ключевых отличий

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

Application × 10

В микросервисной архитектуре можно отдельно увеличить количество экземпляров Catalog Service:

Catalog Service × 10

Order Service × 3

Payment Service × 2

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

Мониторинг и эксплуатация

Чем больше сервисов в системе, тем сложнее понять, что произошло с конкретным пользовательским запросом.

Например:

Frontend → API Gateway → Order Service → Payment Service → Notification Service

Если пользователь получил ошибку при оформлении заказа, недостаточно посмотреть лог только Order Service. Проблема могла возникнуть в Payment Service или на уровне сетевого взаимодействия между компонентами.

Поэтому для микросервисных систем особенно важны:

  • Централизованные логи;
  • Метрики;
  • distributed tracing;
  • correlation/request ID;
  • Мониторинг доступности сервисов;
  • Автоматизированный CI/CD.

Вместо одного приложения команда фактически начинает управлять распределенной системой. Поэтому микросервисная архитектура тесно связана с DevOps-практиками и автоматизацией инфраструктуры.

Монолит и микросервисы: что выбрать

Универсального победителя здесь нет. Выбор зависит от размера системы, бизнес-требований, команды и ожидаемой нагрузки.
Критерий
Монолит
Микросервисы
Деплой
Один основной deployment
Независимый deployment сервисов
Масштабирование
Обычно всего приложения
Отдельных сервисов
Взаимодействие
Вызовы внутри процесса
Сетевые вызовы и события
Работа с данными
Часто общая БД
Обычно данные разделены по сервисам
Тестирование
Проще на уровне системы
Сложнее из-за интеграций
Инфраструктура
Проще
Значительно сложнее
Отказоустойчивость
Меньше сетевых проблем
Нужно учитывать распределенные отказы
Команды
Удобно для небольшой команды
Хорошо подходит нескольким автономным командам
Технологический стек
Обычно единый
Может отличаться между сервисами
Для небольшого продукта с одной командой хорошо спроектированный монолит часто будет рациональнее микросервисов. Здесь можно использовать подход Monolith First: сначала реализовать систему как монолит, а затем, по мере появления реальных потребностей, выделять в отдельные сервисы те компоненты, для которых независимое масштабирование, разработка или деплой действительно дают преимущества.

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

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

Клиент-серверная и микросервисная архитектуры — не конкуренты

Здесь важно вернуться к главному вопросу.

  • Клиент-серверная архитектура отвечает на вопрос: какой вид взаимодействия используется между участниками системы? В этой модели клиент инициирует запрос, а сервер его обрабатывает и возвращает ответ — то есть клиент просит, сервер отвечает.

  • Микросервисная архитектура отвечает на другой вопрос: как организована серверная часть внутри?

Поэтому вполне нормальная система может одновременно быть клиент-серверной и микросервисной:

Web / Mobile Client → API Gateway → Microservices → Databases

Точно так же клиент-серверное приложение может использовать монолит:

Web / Mobile Client → Monolith → Database

То есть противопоставлять «клиент-серверную архитектуру» и «микросервисы» некорректно. Это разные уровни описания системы.

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

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

Хорошая микросервисная архитектура — это не «как можно больше маленьких сервисов». Это система с понятными границами ответственности, контролируемыми зависимостями и обоснованной степенью автономности компонентов.

В конечном счете выбор выглядит не как «монолит или микросервисы», а как поиск подходящей архитектуры под конкретный продукт. Для одного проекта лучшим решением будет простой монолит, для другого — набор независимых сервисов. Главное, чтобы архитектурное решение отвечало реальным требованиям системы, а не само становилось источником ненужной сложности.


Хотите узнать больше? Изучите другие статьи из раздела:
2026-08-19 13:00 Основы и старт в IT