Микросервисы и service mesh
latest update of the page: 31-10-2024, 18:18 UTC
Микросервисы (MSA)
Микросервисная архитектура = метод создания распределённых приложений в виде набора независимо разрабатываемых и развёртываемых в изолированном окружении небольших служб. Является частным случаем SOA.
Признаки микросервисной архитектуры:
- Каждый сервис имеет свой домен (предметную область), сиречь занимается управлением своего собственного набора бизнес-сущностей либо своим особенным набором функций. Например, сервис формирования отчётов, сервис приёма данных в архив, сервис поиска и выдачи данных, сервис сбора метрик или логов. Поэтому такие сервисы и микро-.
- Каждый сервис обычно разрабатывается отдельной командой, возможно даже в отдельном релизном цикле.
- Каждый сервис имеет свой отдельный репозиторий. Команды не мешаются друг другу.
- Каждый сервис имеет свой CI/CD/CDP pipeline и может быть отправлен в ПРОД независимо от других (идёт собственным дистрибутивом).
- Каждый сервис может (но не обязан) включать в себя свой стек технологий. Например, один написан на Golang, другой на Java, третий на C# — на усмотрение команды разработки.
- Каждый сервис имеет свою БД (и СУБД).
Микросервисная архитектура изолирует сбои и повышает устойчивость системы. Монолитное приложение обрушается целиком, когда какой-нибудь несущественный отчёт, запускаемый раз в квартал, может стать причиной деградации всей системы массового обслуживания. Микросервисная архитектура снижает вероятность таких событий.
Поскольку асинхронное событийное взаимодействие — практически стандарт в микросервисной архитектуре, то надо разбираться в создании событийной архитектуры (Event Driven Architecture, см. статью https://habr.com/ru/company/dataart/blog/280083/), а сами микросервисы должны соответствовать требованиям Reactive.
скачать схему в формате diagrams.net (бывший draw.io)
Минусы микросервисной архитектуры
- скорее всего вы будете вынуждены перейти на асинхронное событийное взаимодействие;
- рост накладных расходов — общее снижение скорости работы в сравнении с "монолитом", состоящим из модулей, взаимодействие между которыми вы вынесли вынесли на сетевой уровень, увеличение вероятности потери данных при транспортировке;
- сложнее организовать транзакции.* Транзакция = способ группировки операций чтения / записи в одну логическую единицу, в рамках которой эти операции либо выполняются целиком либо не выполняются с возможностями прерывания и отката.
- архитектура интерационных взаимодействий усложнится, скорее всего вам понадобится организовать трейсинг запросов для облегчения разбора различных проблем;
- теперь критически важно актуальность поддерживать контрактов API (CDC);
- логов теперь больше и они в разных местах — у каждого сервиса свои.
Зачем в микросервисы?
Основные плюсы здесь — с точки зрения процессов:
- независимый деплой (проще тестировать и выкатывать/откатывать по кусочкам)
- гарантия того, что другие команды не сунутся туда, куда им соваться не нужно, и не будет конфликтов при мержах (изоляция)
- форсируется общение через чётко документированное API (нельзя взять и накостылять что-то в обход)
Когда над монолитом работают несколько команд, постоянно что-то отваливается/не собирается, нужно разруливать какие-то конфликты при мержах, другая команда залезла в твой код и накуролесила, поменяли общий класс-зависимость и поведение немного поменялось, но сломало твои кейсы и т.д. (это даже при DDD).
С микросервисами вообще в этом плане лепота — присутствует какая-то стабильность, при переходе от задачи к задаче и мержах старых задач есть уверенность, что оно с вероятностью 99.99% заведется без проблем и будет работать так же, как в прошлый раз оставил.
©
комментарий на habr
Что почитать на тему:
- Microservices (Martin Fowler, 2014) — с этого всё началось.
- Микросервисная архитектура в корпоративном ИТ-ландшафте. Вменяемая комплексная статья о микросервисах в сложном ИТ-ландшафте. Её одну можно рекомендовать взамен 10 стандартных громогласных буллщит-статей о микросервисах.
- Microservices. Как правильно делать и когда применять? ("DataArt", 2016)
- Микросервисная архитектура, подходы и технологии (Кирилл Ветчинкин, 2018). Плюсы, минусы, как проектировать, типовые ошибки/проблемы, способы решения. Да, в презентации есть некоторые ошибки и спорные моменты, но это одна из лучших о микросервисах на мой взгляд.
-
Организация бизнес-процессов при микросервисном подходе:
-
Тестирование:
Service mesh
Что почитать на тему:
- История service mesh в компании (Александр Лукьянченко, Авито, 2019). Об изначальных проблемах, о подходе к Service Mesh, о проблемах с эксплуатацией Istio, о создании собственного решения в виде sidecar-сервиса Netramesh (Golang + K8s / bare metal), о внедрении OpenTracing с инструментом Jaeger (что позволяет получать карты взаимодействия сервисов), о тестах и выделении критичных путей, о своего рода канареечных тестах с подменой роутинга для тестов.
- Что такое Service Mesh? (2020) — коротко о.
- Сценарии использования service mesh (2020)
- Service Mesh: что нужно знать каждому Software Engineer о самой хайповой технологии (2019). Ангажировано Linkerd.
- Что такое service mesh, когда внедрять, альтернативы Istio и другие ответы экспертов с АМА-сессии (2021)
- Трассировка сервисов, OpenTracing и Jaeger
- Как мы в Dropbox перешли с Nginx на Envoy
Кто использует service mesh
Крупные корпорации, банки и прочие предприятия, имеющие сотни (микро)сервисов с очень нагруженной коммуникацией между ними, а также те, кто является владельцем целых платформ.
Пионерами в микросервисной архитектуре и service mesh в ИТ являются Lyft, Netflix и Twitter (ныне — X).
В российских реалиях внедрение происходит в топ-банках и, например, Авито.
Ценность service mesh: предоставление функций, критически важных для работы современного серверного ПО, единообразным для всего стека и независимым от кода приложения образом.
Суть
Service mesh = архитектурный подход, который
- в условиях наличия сотен (микро)сервисов + использования облаков с тысячами инстансов + использования контейнеризации + необходимости обработки больших объёмов межсервисных коммуникаций
- за счёт добавления в инфраструктуру userspace-прокси (data plane), расположенных "рядом" с сервисами, и набора управляющих процессов (control plane)
- позволяет реализовывать такие функции как service discovery + routing + balancing + tracing + authentication + authorization + encryption + circuitBreaking + autoscaling и другие
Data plane перехватывает вызовы между сервисами, производя над ними необходимые манипуляции.
Control plane координирует поведение прокси и обеспечивает доступ для оператора к API, позволяя манипулировать сетью, изменяя её как единое целое.
Service mesh занимается эксплуатационной логикой, а не смысловой. Занятие смысловой логикой было главным недостатком сервисной шины предприятия (ESB).
Сохранение этого разделения помогает service mesh избежать той же участи.
Некоторые технологии и инструменты из области Service mesh
Поясняющая схемка OS, Istio, k8s
(для себя) поясняющая схемка взаимосвязи некоторых сущностей Openshift, Istio, k8s.
В OSE для входа используется Route, в "голом" istio / kubernetes — Ingress.
Разобраться с EnvoyFilter.
скачать схему в формате diagrams.net (бывший draw.io)
Пример набора сущностей для маршрутизации запросов на какой-то внешних хост через эгресс:
# Service. Объявлен граничный порт для сервиса граничного прокси.
kind: Service
apiVersion: v1
metadata:
name: svc-egress
labels:
app: i-egressgateway
app-group: "some-egress"
app.kubernetes.io/part-of: istio
app.kubernetes.io/instance: istio-controlpanel
release: istio
app.kubernetes. io/component: gateways
istio: i-egressgateway
maistra-version: 2.0.2
app.kubernetes.io/name: gateways
chart: gateways
heritage: Tiller
spec:
ports:
- name: http-7074
protocol: TCP
port: 7074
targetPort: 7074
selector:
app: i-egressgateway
istio: i-egressgateway
type: ClusterIP
status:
loadBalancer: {}
----------------------------------------
# ServiceEntry. Описаны для целевого хоста граничный порт и порт удалённой машины
apiVersion: networking.istio.io/v1beta1
kind: ServiceEntry
metadata:
name: se-egressgateway
spec:
exportTo:
- .
hosts:
- remotehostname.com
location: MESH_EXTERNAL
ports:
- name: http-7074
number: 7074
protocol: HTTP
- name: https-8881
number: 8881
protocol: HTTPS
resolution: DNS
----------------------------------------
# VirtualService. Описана маршрутизация в направлении целевого хоста с граничного порта на целевой порт удалённой машины.
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: vs-egressgateway
labels:
app-group: "some-egress"
spec:
exportTo:
- .
gateways:
- mesh
- gw-egressgateway
hosts:
- remotehostname.com
http:
- match:
- gateways:
- mesh
port: 7074
rewrite:
authority: remotehostname.com
route:
- destination:
host: svc-egress
port:
number: 7074
- match:
- gateways:
- gw-egressgateway
port: 7074
rewrite:
authority: remotehostname.com
route:
- destination:
host: remotehostname.com
port:
number: 8881
----------------------------------------
# Gateway. Для эгресса в направлении внешнего хоста указан граничный порт.
apiVersion: networking.istio.io/v1beta1
Kind: Gateway
metadata:
name: gw-egressgateway
labels:
app-group: "some-egress"
spec:
selector:
app: i-egressgateway
istio: i-egressgateway
servers:
- hosts:
- remotehostname.com
port:
name: http-7074
number: 7074
protocol: HTTP
----------------------------------------
# DestinationRule. В направлении внешнего хоста указан целевой порт и необходимые для MTLS сертификаты + ключ.
apiVersion: networking.istio.io/v1beta1
kind: DestinationRule
metadata:
name: dr-egressgateway
labels:
app-group: "some-egress"
spec:
exportTo:
- .
host: remotehostname.com
trafficpolicy:
loadBalancer:
simple: ROUND_ROBIN
portLevelSettings:
- port:
number: 8881
tls:
cacertificates: /etc/ssl/certs/caCertificates.pem
clientCertificate: /etc/ssl/certs/tls.crt
mode: MUTUAL
privatekey: /etc/ssl/certs/tls.key
sni: remotehostname.com
outlierDetection:
consecutive5xxErrors: 7
interval: 5m
baseEjectionTime: 15m