Microservices Design Guide

Det er 2018, alle har hørt om Microservices. Men ved du hvordan man designer en?

Microservices er et populært emne blandt softwareingeniører i dag. Lad os forstå, hvordan vi kan opbygge virkelig modulære, forretningsmæssige smidige IT-systemer med Microservices arkitektonisk stil.

Mikroservices-koncept

Mikroservices-arkitektur består af samlinger af lette, sammenkoblede tjenester. Hver service implementerer en enkelt forretningsfunktion. Ideelt set skal disse tjenester være sammenhængende nok til at udvikle, teste, frigive, distribuere, skalere, integrere og vedligeholde uafhængigt.

Formel definition
”Microservice arkitektonisk stil er en tilgang til at udvikle en enkelt applikation som en pakke med små tjenester, der hver kører i sin egen proces og kommunikerer med lette mekanismer, ofte et HTTP-ressource API. Disse tjenester er bygget op omkring forretningsmæssige kapaciteter og uafhængigt kan implementeres af fuldautomatiseret installationsapparat. Der er et minimum af centraliseret styring af disse tjenester, der kan skrives på forskellige programmeringssprog og bruger forskellige datalagringsteknologier. ”
- James Lewis og Martin Fowler

Definition af egenskaber ved mikroservices

  • Hver service er en let, uafhængig og løst koblet forretningsenhed.
  • Hver service har sin egen kodebase, der administreres og udvikles af et lille team (for det meste i et smidigt miljø).
  • Hver service er ansvarlig for en enkelt del af funktionaliteten (forretningsevne) og gør det godt.
  • Hver service kan vælge den bedste teknologistakke til brugssager (ikke nødvendigt at holde fast i en ramme i hele applikationen).
  • Hver service har sin egen DevOp-plan (test, frigivelse, implementering, skalering, integrering og vedligeholdelse uafhængigt).
  • Hver service distribueres i et selvstændigt miljø.
  • Tjenester kommunikerer med hinanden ved hjælp af veldefinerede API'er (smarte slutpunkter) og enkle protokoller som REST over HTTP (stomme rør).
  • Hver service er ansvarlig for at opretholde sine egne data og bevare ekstern tilstand (kun hvis flere tjenester forbruger de samme data, håndteres sådanne situationer i et fælles datalag).

Fordele ved mikroservices

Microservice er lavet til at skalere store systemer. De er også gode muligheder for kontinuerlig integration og levering.

Scale Cube: 3-dimensionel model til skalerbarhed (Billede: Nginx Blog)
  • Uafhængig skalering - Microservices-arkitektur understøtter Scale Cube-konceptet, der er beskrevet i den fremragende bog The Art of Scalability. Når man udvikler mikroservices for at opnå funktionel nedbrydning, skalerer applikationen automatisk via Y-aksen. Når forbruget er stort, kan mikroservices skalere via X-aksen ved at klone med mere CPU og hukommelse. Til distribution af data på flere maskiner kan store databaser adskilles (afskærmning) i mindre, hurtigere og lettere styrede dele, der muliggør skalering af Z-aksen.
  • Uafhængige udgivelser og implementeringer - Fejlrettelser og funktionsudgivelser er mere håndterbare og mindre risikable med mikroservices. Du kan opdatere en service uden at omdisponere hele applikationen og rulle tilbage eller rulle en opdatering frem, hvis noget går galt.
  • Uafhængig udvikling - Hver service har sin egen kodebase, som er udviklet, testet og implementeret af et lille fokuseret team. Udviklere kan kun fokusere på en service og relativt lille rækkevidde. Dette resulterer i forbedret produktivitet, projekthastighed, kontinuerlig innovation og kvalitet ved kilden.
  • Behagelig nedbrydning - Hvis en tjeneste går ned, forplantes dens virkning ikke til resten af ​​applikationen og resulterer i en katastrofal fiasko i systemet, hvilket tillader en vis grad af skrøbelighed at manifestere sig.
  • Decentral styring - Udviklere kan frit vælge teknologibunkerne og tage designstandarder og implementeringsbeslutninger, der er bedst egnet til deres service. Hold behøver ikke at blive straffet på grund af tidligere teknologiske beslutninger.

Operationelle bekymringer

Uafhængige tjenester alene kan ikke danne et system. For den rigtige succes med mikroservicearkitektur kræves betydelige investeringer for at håndtere tværgående systemproblemer som:

  • Servicereplikation - en mekanisme, hvorpå tjenester let kan skaleres på baggrund af metadata
  • Service registrering og opdagelse - en mekanisme, der muliggør opslag af tjenester og finder slutpunktet for hver tjeneste
  • Tjenesteovervågning og logning - en mekanisme til at samle logfiler fra forskellige mikroservices og give en konsekvent rapportering
  • Resiliency - en mekanisme for tjenester, der automatisk tager korrigerende handlinger under fejl
  • DevOps - en mekanisme til håndtering af kontinuerlig integration og implementering (CI og CD)
  • API gateway - en mekanisme til tilvejebringelse af et indgangspunkt for klienter

Middleware & designmønstre

API Gateway (Enkelt indgangspunkt for alle klienter)

API Gateway Style Microservices Architecture (Image: Microsoft Azure Docs) - dette er det mest almindelige designmønster, der bruges i mikroservices. API Gateway er en formidler med minimale rutefunktioner og fungerer bare som et 'dumt rør' uden forretningslogik indeni. Generelt giver API Gateway dig mulighed for at forbruge et administreret API over REST / HTTP. Andre typer mikroservices-integrationsmønstre: Point-to-point-stil (påkalde tjenester direkte fra klientsiden-app) og Message Broker-stil (implementering af asynkron messaging).

API Gateway fungerer som et enkelt indgangspunkt for alle klienter såvel som en kanttjeneste til at eksponere mikroservices for omverdenen som administrerede API'er. Det lyder som en omvendt proxy, men har også yderligere opgaver som simpel belastningsbalancering, godkendelse og autorisation, fejlhåndtering, revision, protokoloversættelser og routing. Udviklingsteamet kan vælge en af ​​følgende fremgangsmåder til implementering af en API Gateway.

  • Byg det programmatiske - for at få bedre tilpasninger og kontrol
  • Distribuer et eksisterende API-gateway-produkt - for at spare den første udviklingstid og bruge avancerede indbyggede funktioner (Ulemper: Sådanne produkter er leverandørafhængige og ikke helt gratis. Konfigurationer og vedligeholdelse kan ofte være kedelige og tidskrævende)

Nogle designmønstre, der forklarer API Gateway-opførsel, er som følger (Læs designmønstre til mikroservices).

  • Gateway Aggregation - samlet flere klientanmodninger (normalt HTTP-anmodninger), der er målrettet mod flere interne mikroservices til en enkelt klientanmodning, hvilket reducerer chattiness og latens mellem forbrugere og tjenester.
  • Gateway-offloading - aktiver individuelle mikroservices til at downloade deres delte servicefunktionalitet til API-gateway-niveau. Sådanne tværgående funktionaliteter inkluderer autentificering, godkendelse, serviceopdagelse, fejltolerancemekanismer, QoS, belastningsbalancering, logging, analyse osv.
  • Gateway Routing (routing af lag 7, normalt HTTP-anmodninger) - ruteanmodninger til endepunkterne for interne mikroservices ved hjælp af et enkelt endepunkt, så forbrugerne ikke behøver at styre mange separate endepunkter

Bemærk, at en API Gateway altid skal være en meget tilgængelig og performant komponent, da det er indgangspunktet for hele systemet.

Begivenhedsbus (pub / sub-mægler-kanal til asynkron hændelsesdrevet kommunikation)

Eventuel konsistens mellem mikroservices baseret på begivenhedsdrevet async-kommunikation (Image: microsoft.com)

For forskellige dele af applikationen til at kommunikere med hinanden uanset rækkefølgen af ​​meddelelser (asynkron) eller hvilket sprog de bruger (sprogagnostisk), kan hændelsesbus bruges. De fleste af begivenhedsbusser understøtter offentliggørelse / abonnement, distribuering, point to point og anmodning-svar messaging. Nogle begivenhedsbusser (som i Vert.x) giver klientsiden mulighed for at kommunikere med tilsvarende serverknudepunkter ved hjælp af den samme begivenhedsbus, som er en cool funktion, der er elsket af full-stack-teams.

Servicemesh (Sidevogn til kommunikation mellem tjenester)

Interservice-kommunikation ved hjælp af Service Mesh-stil (Image: Microservices in Practice)Hvordan servicemasker bruges i en applikation (Billede: christianposta.com)

Service Mesh implementerer Sidecar-mønster ved at tilvejebringe hjælperinfrastruktur til kommunikation mellem services. Det inkluderer funktioner som elasticitet (fejltolerance, belastningsbalancering), opdagelse af tjenester, routing, observerbarhed, sikkerhed, adgangskontrol, support til kommunikationsprotokol osv.

Hvordan servicemasker passer ind i netværkstakken (Billede: christianposta.com)

I praksis distribueres et Sidecar-eksempel ved siden af ​​hver tjeneste (ideelt i den samme container). De kan kommunikere gennem primitive netværksfunktioner af tjenesten. Control Plane of Service Mesh distribueres separat for at give centrale funktioner som serviceopdagelse, adgangskontrol og observerbarhed (overvågning, distribueret logning). Vigtigst er det, at Service Mesh-stil tillader udviklere at afkoble netværkskommunikationsfunktioner fra mikroservicekode og holde tjenester kun fokuseret på forretningsmulighederne. (Læs: Netflix Prana, servicemesh for mikroservices)

Selvom ovenstående billeder indikerer direkte forbindelser mellem tjenester, ville den dejlige måde at håndtere kommunikation mellem services være at bruge en simpel Event Bus som mægler til at holde koblingen på et minimumsniveau.

Backends for Frontends (BFF)

Implementering af backends til frontender og aggregeringsmønstre på API gateway-niveau (Billede: microsoft.com)

Hvis applikationen skal skræddersy hver API for at passe til klient-apptypen (web, mobil, forskellige platforme), kan forskellige regler (konfigs) håndhæves via en facade eller kan tjene separate builds baseret på klientfunktioner. Dette kan implementeres på selve API Gateway-niveau eller parallelt med serviceniveauet. Dette mønster er nyttigt til at give specifikke brugeroplevelser. Udviklingsholdet skal dog være forsigtigt nok til at holde BFF'er op til en overskuelig grænse.

Bedste praksis

Design af domæner - Modeltjenester omkring forretningsområdet.

For at håndtere store modeller og teams kan Domain Driven Design (DDD) anvendes. Den beskæftiger sig med store modeller ved at dele dem op i forskellige bundne sammenhænge og være eksplicit om deres indbyrdes forhold og underliggende domæne. Disse afgrænsede kontekster kan konverteres til separate mikroservices på applikationsdesignniveau (Læs: Bounded Context i Domain-Driven Design).

Decentral datahåndtering (Undgå delte databaser). Når flere tjenester forbruger et delt dataskema, kan det skabe stram kobling i datalaget. For at undgå det skal hver tjeneste have sin egen datatilgangslogik og separat datalager. Udviklingsholdet kan frit vælge den metod for persistens for data, der bedst passer til hver tjeneste og datatype.

Undgå delte datalagre og mekanismer til adgang til data (Billede: christianposta.com)

Smart slutpunkter og stomme rør - Hver service ejer et veldefineret API til ekstern kommunikation. Undgå lækker implementeringsdetaljer. Til kommunikation skal du altid bruge enkle protokoller, såsom REST over HTTP.

Asynkron kommunikation - Når der anvendes asynkron kommunikation på tværs af tjenester, blokeres dataflyten ikke for andre tjenester.

Synkron vs. asynkron meddelelse (Billede: microsoft.com)

Undgå kobling mellem tjenester - Tjenesterne skal have løs kobling og høj funktionel samhørighed. De vigtigste årsager til kobling inkluderer delte databaseskemaer og stive kommunikationsprotokoller.

Decentraliser udviklingen - Undgå at dele codebaser, dataskemaer eller udviklingsholdmedlemmer blandt flere tjenester / projekter. Lad udviklere fokusere på innovation og kvalitet ved kilden.

Opbevar domæneviden ud af gatewayen. Lad gateway håndtere routing og tværgående problemer (godkendelse, SSL-terminering).

Token-baseret autentificering - I stedet for at implementere sikkerhedskomponenter på hvert mikroserviceniveau, der taler til et centraliseret / delt brugerlager og hente godkendelsesinformationen, skal du overveje at implementere godkendelse på API Gateway-niveau med vidt anvendte API-sikkerhedsstandarder som OAuth2 og OpenID Opret forbindelse. Efter at have fået en autorisationstoken fra autorisationsudbyderen, kan den bruges til at kommunikere med andre mikroservices.

Microservice-sikkerhed med OAuth2 og OpenID Connect (Billede: Kasuns blog)

Begivenhedsstyret natur - Mennesker er autonome agenter, der kan reagere på begivenheder. Kan vores systemer ikke være sådan? (Læs: Hvorfor mikroservices skal udføres af begivenheder: Autonomi vs autoritet)

Eventuel konsistens - På grund af den høje sammenhæng i mikroservices er det svært at opnå stærk konsistens i hele systemet. Udviklingshold bliver nødt til at håndtere eventuel konsistens, som det kommer.

Fejltolerance - Da systemet består af flere tjenester og middleware-komponenter, kan der opstå fejl meget nemt et sted. Implementering af mønstre som kredsløb, skott, genforsøg, timeouts, fejler hurtigt, failover-cache, hastighedsbegrænsere, belastningslister i sådanne sårbare komponenter kan minimere risikoen for større fejl. (Læs: Designe en mikroservicearkitektur til fiasko)

Produktionsteknologi - Microservices fungerer godt, så længe det er konstrueret som et produkt, ikke som et projekt. Det handler ikke om at få det til at arbejde på en eller anden måde og levere inden fristerne, men om et langsigtet engagement med teknisk ekspertise.

Mikroservices i praksis

Hvornår skal man bruge Microservices

Microservices-arkitektur passer bedst til:

  • Anvendelser med høje skalerbarhedsbehov
  • Projekter med høj frigivelseshastighed
  • Forretningssager med rige domæner eller mange underdomæner
  • Agile miljøer med små, tværfunktionelle udviklingsteams, der udvikler store produkter i samarbejde (Læs: The Real Success Story of Microservices Architectures)

Nogle gå til rammer til implementering af mikroservices

  • Vert. giver kun nyttige mursten, udviklere har frihed til at være innovative og omhyggeligt bygge deres applikationer, ikke som traditionelle restriktive rammer)
  • Akka - tilfredsstillende ydelse, implementerer skuespillermodel, god til reaktive & begivenhedsdrevne mikroservices
  • SpringBoot / Cloud - let at starte (velkendte paradigmer), baseret på den gode gamle forårramme, lidt tunge ramme, mange tilgængelige integrationer, stort samfundsstøtte
  • Dropwizard - god til hurtig udvikling af RESTful webtjenester, leveres fuldt udstyret med nogle af dejlige Java-værktøjer og biblioteker som Google Guava, Jetty-server, Logback, Hibernate Validator, Joda Time, Jersey og Jackson.

Distributionsmuligheder

  • Containere - gode til at håndhæve DevOp-mål (hurtig udvikling, reduceret tid til marked, problemfri skalering)
  • Cloud - godt til at opbygge pålidelig og skalerbar infrastruktur til at betjene geografisk spredte brugere
  • Serverløs - god til håndtering af meget flygtige trafikker
  • Vedligehold egen IT-infrastruktur - godt for dem, der har stor kapacitet og ressourcer til at bygge hele infrastrukturen

Udvikling af koncepter omkring mikroservices

  • Selvbeholdte systemer - saml software fra uafhængige systemer (som lodrette i mikroservices)
  • Micro Frontends - opdeler monolit web UI'er i uafhængige funktioner, der kan udvikles som selvstændige UI-komponenter og kommunikere direkte med mikroservices

Nøgleord til at google (og studere!)

Domain Driven Design (DDD) | Bounded Context (BC) | Polyglot Persistence (PP) | Kommando- og forespørgselsansvarssegregation (CQRS) | Kommandosøgeseparation (CQS) | Event-Sourcing (ES) | CAP-sætning | Eventuel konsistens | Tolv-faktor app | SOLID-principper |

Arkitekturforslag

Microservices-arkitektur til en online shopping-applikation (Image: microsoft.com) - Denne arkitektur foreslås af Microsoft-udviklere ved hjælp af Microsoft-teknologier. Her er API Gateway skræddersyet til at behandle web- og mobilbrugere forskelligt. For datalag udvælges datalagringsteknologier omhyggeligt i henhold til forretningsfunktionerne (relationelle databaser for strukturerede data, Redis til midlertidig datacache, MongoDB og CosmosDB til ustrukturerede data). Interservice-kommunikation, der håndteres af eventbussen. Hvis man holder teknologier til side, er dette det mest almindelige integrationsmønster, der bruges i mikroservicebaserede applikationer.Mikroservices-arkitektur til en applikation, der viser realtidsopdateringer til slutbrugere ved hjælp af store mængder inputdatastrømme, der kommer fra forskellige begivenhedskilder (f.eks. Trafikdata, vejrlæsning, aktiemarkedsfeeds, sociale mediaposter, sensoroutput). Disse inputdatastrømme indsamles oprindeligt af en hændelseslog implementeret ved hjælp af Kafka. Det fortsætter data på disken og kan derfor bruges til batchforbrugsformål (analytics, rapportering, data science, backup, revision) eller sendes til realtidsforbrugsformål (operationelle analyser, CEP, admin dashboards, alarm apps). I henhold til dette diagram er den kontinuerlige indkommende strøm imidlertid opdelt i mikrobatches med specificerede intervaller ved hjælp af Spark og ført ind i WSO2 Siddhi CEP-motoren. Derefter identificerer den begivenhederne og vedvarer dem i ustrukturerede former ved hjælp af MongoDB-datalagre. Mikroservices forbruger disse data og vises for slutbrugerne. Hvis du omhyggeligt ser på designet, da Vert.x begivenhedsbuss har evnen til at oprette forbindelser med frontend UI-komponenter, er denne funktion brugt til effektiv opdatering af kun de relevante dele i UI. Når man holder teknologier til side, er dette en fantastisk arkitektur til begivenhedsdrevet ikke-blokerende mikroservicebaseret applikation.Cloud-native omni-channel mikroservices-arkitektur til en ordrestyringsapplikation (Image: ibm.com) - En vigtig specialitet i dette design er, i stedet for at bruge en API Gateway, har IBM-arkitekter foreslået et kantlag med separate backends for hver klientside-kanal ( mobile apps, webapps, IOT-enheder, API-forbrugere). En anden specialitet er, at mikroservicelaget er opdelt i 2 underlag kaldet Business Logic-lag og Foundational-lag. Foundational Layer (a.k.a. Core Services Layer) beskæftiger sig med vedholdenheds- og integrationsopgaver ved hjælp af forskellige cloud-native tjenester (cloud-datalagre, Elasticsearch-motorer, der integrerer og indekserer en Watson-samtale). Business Logic-lag integrerer data fra Foundational-laget og leverer meningsfulde forretningsfunktioner. Dette ville være en fantastisk arkitektur til at betjene et meget stort antal brugerbaser, som er geografisk spredt og adgang til applikation via forskellige platforme.
Nyder det hidtil? Glem ikke at anbefale