BLOG | NGINX

Ereignisgesteuertes Datenmanagement für Microservices

NGINX-Teil-von-F5-horiz-schwarz-Typ-RGB
Chris Richardson Miniaturbild
Chris Richardson
Veröffentlicht am 04. Dezember 2015

Redaktion – Die siebenteilige Artikelserie ist nun komplett:

  1. Einführung in Microservices
  2. Erstellen von Microservices: Verwenden eines API-Gateways
  3. Erstellen von Microservices: Interprozesskommunikation in einer Microservices-Architektur
  4. Service Discovery in einer Microservices-Architektur
  5. Ereignisgesteuertes Datenmanagement für Microservices (dieser Artikel)
  6. Auswählen einer Bereitstellungsstrategie für Microservices
  7. Refactoring eines Monolithen in Microservices

Sie können den kompletten Artikelsatz sowie Informationen zur Implementierung von Microservices mit NGINX Plus auch als E-Book herunterladen – Microservices: Vom Entwurf bis zur Bereitstellung . Und sehen Sie sich unsere Serie zur Microservices-Referenzarchitektur und die Seite mit Microservices-Lösungen an.

Dies ist der fünfte Artikel einer Reihe über das Erstellen von Anwendungen mit Microservices. Der erste Artikel stellt das Microservices-Architekturmuster vor und diskutiert die Vorteile und Nachteile der Verwendung von Microservices. Der zweite<.htmla> und dritte Artikel der Reihe beschreiben verschiedene Aspekte der Kommunikation innerhalb einer Microservices-Architektur. Der vierte Artikel untersucht das eng damit verbundene Problem der Diensterkennung. In diesem Artikel ändern wir das Thema und betrachten die Probleme der verteilten Datenverwaltung, die in einer Microservices-Architektur auftreten.

Microservices und das Problem der verteilten Datenverwaltung

Eine monolithische Anwendung verfügt normalerweise über eine einzelne relationale Datenbank. Ein wesentlicher Vorteil der Verwendung einer relationalen Datenbank besteht darin, dass Ihre Anwendung ACID-Transaktionen verwenden kann, die einige wichtige Garantien bieten:

  • Atomarität – Änderungen werden atomar vorgenommen
  • Konsistenz – Der Zustand der Datenbank ist immer konsistent
  • Isolation – Auch wenn Transaktionen gleichzeitig ausgeführt werden, scheint es, als würden sie seriell ausgeführt.
  • Dauerhaftigkeit – Sobald eine Transaktion abgeschlossen ist, kann sie nicht mehr rückgängig gemacht werden.

Dadurch kann Ihre Anwendung einfach eine Transaktion starten, mehrere Zeilen ändern (einfügen, aktualisieren und löschen) und die Transaktion festschreiben.

Ein weiterer großer Vorteil der Verwendung einer relationalen Datenbank besteht darin, dass sie SQL bereitstellt, eine umfangreiche, deklarative und standardisierte Abfragesprache. Sie können ganz einfach eine Abfrage schreiben, die Daten aus mehreren Tabellen kombiniert. Der RDBMS-Abfrageplaner ermittelt dann die optimale Möglichkeit zur Ausführung der Abfrage. Sie müssen sich nicht um Details auf niedriger Ebene kümmern, beispielsweise um den Zugriff auf die Datenbank. Und da sich alle Daten Ihrer Anwendung in einer Datenbank befinden, können sie problemlos abgefragt werden.

Leider wird der Datenzugriff viel komplexer, wenn wir zu einer Microservices-Architektur wechseln. Das liegt daran, dass die Daten, die jedem Microservice gehören , privat für diesen Microservice sind und nur über seine API abgerufen werden können. Durch die Kapselung der Daten wird sichergestellt, dass die Microservices lose gekoppelt sind und sich unabhängig voneinander weiterentwickeln können. Wenn mehrere Dienste auf dieselben Daten zugreifen, erfordern Schemaaktualisierungen zeitaufwändige, koordinierte Aktualisierungen aller Dienste.

Erschwerend kommt hinzu, dass unterschiedliche Microservices oft unterschiedliche Arten von Datenbanken verwenden. Moderne Anwendungen speichern und verarbeiten unterschiedliche Arten von Daten und eine relationale Datenbank ist nicht immer die beste Wahl. Für einige Anwendungsfälle verfügt eine bestimmte NoSQL-Datenbank möglicherweise über ein praktischeres Datenmodell und bietet eine deutlich bessere Leistung und Skalierbarkeit. Beispielsweise ist es für einen Dienst, der Text speichert und abfragt, sinnvoll, eine Textsuchmaschine wie Elasticsearch zu verwenden. Ebenso sollte ein Dienst, der Daten zu sozialen Graphen speichert, wahrscheinlich eine Graphdatenbank wie Neo4j verwenden. Aus diesem Grund verwenden auf Microservices basierende Anwendungen häufig eine Mischung aus SQL- und NoSQL-Datenbanken, den sogenannten polyglotten Persistenzansatz.

Eine partitionierte, polyglot-persistente Architektur zur Datenspeicherung bietet viele Vorteile, darunter lose gekoppelte Dienste sowie bessere Leistung und Skalierbarkeit. Allerdings bringt es einige Herausforderungen im Bereich der verteilten Datenverwaltung mit sich.

Die erste Herausforderung besteht darin, Geschäftstransaktionen so zu implementieren, dass die Konsistenz über mehrere Dienste hinweg gewahrt bleibt. Um zu sehen, warum dies ein Problem ist, sehen wir uns das Beispiel eines B2B-Onlineshops an. Der Kundenservice verwaltet Informationen über Kunden, einschließlich ihrer Kreditlinien. Der Bestellservice verwaltet Bestellungen und muss überprüfen, dass eine neue Bestellung das Kreditlimit des Kunden nicht überschreitet. In der monolithischen Version dieser Anwendung kann der Bestellservice einfach eine ACID-Transaktion verwenden, um das verfügbare Guthaben zu überprüfen und die Bestellung zu erstellen.

Im Gegensatz dazu sind in einer Microservices-Architektur die Tabellen ORDER und CUSTOMER für ihre jeweiligen Dienste privat, wie im folgenden Diagramm dargestellt.

Jeder Dienst in einer Microservices-Architektur verwaltet eine private Datenbanktabelle

Der Bestellservice kann nicht direkt auf die Tabelle KUNDE zugreifen. Es kann nur die vom Kundendienst bereitgestellte API verwendet werden. Der Bestelldienst könnte möglicherweise verteilte Transaktionen verwenden, auch als Zwei-Phasen-Commit (2PC) bezeichnet. Allerdings ist 2PC in modernen Anwendungen normalerweise keine praktikable Option. Das CAP-Theorem erfordert, dass Sie zwischen Verfügbarkeit und Konsistenz im ACID-Stil wählen, und Verfügbarkeit ist normalerweise die bessere Wahl. Darüber hinaus unterstützen viele moderne Technologien, wie die meisten NoSQL-Datenbanken, 2PC nicht. Die Aufrechterhaltung der Datenkonsistenz über Dienste und Datenbanken hinweg ist von entscheidender Bedeutung, daher benötigen wir eine andere Lösung.

Die zweite Herausforderung besteht darin, Abfragen zu implementieren, die Daten von mehreren Diensten abrufen. Stellen wir uns beispielsweise vor, dass die Anwendung einen Kunden und seine letzten Bestellungen anzeigen muss. Wenn der Bestellservice eine API zum Abrufen der Bestellungen eines Kunden bereitstellt, können Sie diese Daten mithilfe eines anwendungsseitigen Join abrufen. Die Anwendung ruft den Kunden vom Kundenservice und die Bestellungen des Kunden vom Bestellservice ab. Nehmen wir jedoch an, dass der Bestelldienst nur die Suche nach Bestellungen anhand ihres Primärschlüssels unterstützt (möglicherweise verwendet er eine NoSQL-Datenbank, die nur Abrufe basierend auf Primärschlüsseln unterstützt). In dieser Situation gibt es keine offensichtliche Möglichkeit, die benötigten Daten abzurufen.

Ereignisgesteuerte Architektur

Für viele Anwendungen besteht die Lösung in der Verwendung einer ereignisgesteuerten Architektur . In dieser Architektur veröffentlicht ein Microservice ein Ereignis, wenn etwas Bemerkenswertes passiert, beispielsweise wenn er eine Geschäftseinheit aktualisiert. Andere Microservices abonnieren diese Ereignisse. Wenn ein Microservice ein Ereignis empfängt, kann er seine eigenen Geschäftseinheiten aktualisieren, was zur Veröffentlichung weiterer Ereignisse führen kann.

Mit Ereignissen können Sie dienstübergreifende Geschäftstransaktionen umsetzen. Eine Transaktion besteht aus einer Reihe von Schritten. Jeder Schritt besteht aus einem Mikrodienst, der eine Geschäftsentität aktualisiert und ein Ereignis veröffentlicht, das den nächsten Schritt auslöst. Die folgende Diagrammsequenz zeigt, wie Sie bei der Auftragserstellung ereignisgesteuert das verfügbare Guthaben prüfen können. Die Microservices tauschen Ereignisse über einen Message Broker aus.

  1. Der Bestellservice erstellt eine Bestellung mit dem Status „NEU“ und veröffentlicht ein Ereignis „Bestellung erstellt“.

    Im ersten Schritt einer Bonitätsprüfung in einer Microservices-Architektur veröffentlicht der Bestellservice ein „Bestellung erstellt“-Ereignis.

  2. Der Kundenservice nutzt das Ereignis „Bestellung erstellt“, reserviert Guthaben für die Bestellung und veröffentlicht ein Ereignis „Guthaben reserviert“.

    In einer Microservices-Architektur besteht der zweite Schritt einer Kreditprüfung darin, dass der Kundenservice ein „Kredit reserviert“-Ereignis generiert.

  3. Der Bestellservice nutzt das Ereignis „Guthaben reserviert“ und ändert den Status der Bestellung in „OFFEN“.

    In einer Microservices-Architektur besteht der dritte Schritt einer Bonitätsprüfung darin, dass der Bestellservice den Bestellstatus auf „Offen“ setzt.

Ein komplexeres Szenario könnte zusätzliche Schritte umfassen, wie etwa die Reservierung von Lagerbeständen während der gleichzeitigen Prüfung der Kreditwürdigkeit des Kunden.

Vorausgesetzt, dass (a) jeder Dienst die Datenbank atomar aktualisiert und ein Ereignis veröffentlicht – mehr dazu später – und (b) der Message Broker garantiert, dass Ereignisse mindestens einmal übermittelt werden, können Sie Geschäftstransaktionen implementieren, die sich über mehrere Dienste erstrecken. Es ist wichtig zu beachten, dass dies keine ACID-Transaktionen sind. Sie bieten viel schwächere Garantien, wie beispielsweise die eventuelle Konsistenz . Dieses Transaktionsmodell wird als BASE-Modell bezeichnet.

Sie können Ereignisse auch verwenden, um materialisierte Ansichten zu verwalten, die Daten im Besitz mehrerer Microservices vorab verknüpfen. Der Dienst, der die Ansicht verwaltet, abonniert die relevanten Ereignisse und aktualisiert die Ansicht. Beispielsweise abonniert der Customer Order View Updater Service, der eine Kundenauftragsansicht verwaltet, die vom Kundenservice und Auftragsservice veröffentlichten Ereignisse.

In einer Microservices-Architektur kann ein Dienst Ereignisbenachrichtigungen abonnieren, die von anderen Diensten als Auslöser für Aktionen veröffentlicht werden.

Wenn der Customer Order View Updater Service ein Kunden- oder Bestellereignis empfängt, aktualisiert er den Customer Order View-Datenspeicher. Sie könnten die Kundenbestellansicht mithilfe einer Dokumentdatenbank wie MongoDB implementieren und für jeden Kunden ein Dokument speichern. Der Customer Order View-Abfragedienst verarbeitet Anfragen für einen Kunden und aktuelle Bestellungen, indem er den Customer Order View-Datenspeicher abfragt.

Eine ereignisgesteuerte Architektur hat mehrere Vor- und Nachteile. Es ermöglicht die Implementierung von Transaktionen, die sich über mehrere Dienste erstrecken und letztendliche Konsistenz gewährleisten. Ein weiterer Vorteil besteht darin, dass eine Anwendung dadurch auch materialisierte Ansichten verwalten kann. Ein Nachteil ist, dass das Programmiermodell komplexer ist als bei der Verwendung von ACID-Transaktionen. Zur Behebung von Fehlern auf Anwendungsebene müssen Sie häufig Ausgleichstransaktionen durchführen. Beispielsweise müssen Sie eine Bestellung stornieren, wenn die Bonitätsprüfung fehlschlägt. Darüber hinaus müssen Anwendungen mit inkonsistenten Daten umgehen. Der Grund hierfür ist, dass durch laufende Transaktionen vorgenommene Änderungen sichtbar sind. Die Anwendung kann auch Inkonsistenzen feststellen, wenn sie aus einer materialisierten Ansicht liest, die noch nicht aktualisiert wurde. Ein weiterer Nachteil besteht darin, dass Abonnenten doppelte Ereignisse erkennen und ignorieren müssen.

Atomarität erreichen

In einer ereignisgesteuerten Architektur besteht außerdem das Problem, die Datenbank atomar zu aktualisieren und ein Ereignis zu veröffentlichen. Beispielsweise muss der Bestelldienst eine Zeile in die ORDER-Tabelle einfügen und ein Ereignis „Bestellung erstellt“ veröffentlichen. Es ist wichtig, dass diese beiden Vorgänge atomar ausgeführt werden. Wenn der Dienst nach der Aktualisierung der Datenbank, aber vor der Veröffentlichung des Ereignisses abstürzt, wird das System inkonsistent. Die Standardmethode zum Sicherstellen der Atomarität besteht in der Verwendung einer verteilten Transaktion, an der die Datenbank und der Message Broker beteiligt sind. Aus den oben beschriebenen Gründen, beispielsweise aufgrund des CAP-Theorems, ist dies jedoch genau das, was wir nicht tun möchten.

Veröffentlichen von Ereignissen mithilfe lokaler Transaktionen

Eine Möglichkeit zum Erreichen der Atomarität besteht darin, dass die Anwendung Ereignisse mithilfe eines mehrstufigen Prozesses veröffentlicht, an dem nur lokale Transaktionen beteiligt sind . Der Trick besteht darin, in der Datenbank, in der der Status der Geschäftseinheiten gespeichert wird, eine EVENT-Tabelle zu haben, die als Nachrichtenwarteschlange fungiert. Die Anwendung startet eine (lokale) Datenbanktransaktion, aktualisiert den Status der Geschäftsentitäten, fügt ein Ereignis in die EVENT-Tabelle ein und führt einen Commit für die Transaktion aus. Ein separater Anwendungsthread oder -prozess fragt die EVENT-Tabelle ab, veröffentlicht die Ereignisse im Message Broker und verwendet dann eine lokale Transaktion, um die Ereignisse als veröffentlicht zu markieren. Das folgende Diagramm zeigt den Aufbau.

Erreichen Sie in einer Microservices-Architektur Atomizität, indem Sie zum Veröffentlichen von Ereignissen ausschließlich lokale Transaktionen verwenden.

Der Bestelldienst fügt eine Zeile in die ORDER-Tabelle und ein „Bestellung erstellt“-Ereignis in die EVENT-Tabelle ein. Der Event Publisher-Thread oder -Prozess fragt die EVENT-Tabelle nach unveröffentlichten Ereignissen ab, veröffentlicht die Ereignisse und aktualisiert dann die EVENT-Tabelle, um die Ereignisse als veröffentlicht zu markieren.

Dieser Ansatz hat mehrere Vor- und Nachteile. Ein Vorteil besteht darin, dass garantiert wird, dass für jedes Update ein Ereignis veröffentlicht wird, ohne dass man sich auf 2PC verlassen muss. Außerdem veröffentlicht die Anwendung Ereignisse auf Geschäftsebene, sodass diese nicht mehr abgeleitet werden müssen. Ein Nachteil dieses Ansatzes besteht darin, dass er potenziell fehleranfällig ist, da der Entwickler daran denken muss, Ereignisse zu veröffentlichen. Eine Beschränkung dieses Ansatzes besteht darin, dass seine Implementierung bei Verwendung einiger NoSQL-Datenbanken aufgrund ihrer eingeschränkten Transaktions- und Abfragefunktionen schwierig ist.

Dieser Ansatz macht 2PC überflüssig, da die Anwendung lokale Transaktionen verwendet, um den Status zu aktualisieren und Ereignisse zu veröffentlichen. Sehen wir uns nun einen Ansatz an, der Atomarität dadurch erreicht, dass die Anwendung lediglich den Status aktualisiert.

Mining eines Datenbank-Transaktionsprotokolls

Eine andere Möglichkeit, Atomizität ohne 2PC zu erreichen, besteht darin, dass die Ereignisse von einem Thread oder Prozess veröffentlicht werden, der das Transaktions- oder Commit-Protokoll der Datenbank durchsucht. Die Anwendung aktualisiert die Datenbank, was dazu führt, dass Änderungen im Transaktionsprotokoll der Datenbank aufgezeichnet werden. Der Transaction Log Miner-Thread oder -Prozess liest das Transaktionsprotokoll und veröffentlicht Ereignisse an den Message Broker. Das folgende Diagramm zeigt den Aufbau.

Erreichen Sie in einer Microservices-Architektur Atomizität, indem Sie das Transaktionsprotokoll nach Ereignissen durchsuchen.

Ein Beispiel für diesen Ansatz ist das Open-Source-Projekt LinkedIn Databus . Databus durchsucht das Oracle-Transaktionsprotokoll und veröffentlicht Ereignisse, die den Änderungen entsprechen. LinkedIn verwendet Databus, um die Konsistenz verschiedener abgeleiteter Datenspeicher mit dem Aufzeichnungssystem zu gewährleisten.

Ein weiteres Beispiel ist der Streams-Mechanismus in AWS DynamoDB , einer verwalteten NoSQL-Datenbank. Ein DynamoDB-Stream enthält die zeitlich geordnete Abfolge der Änderungen (Erstellungs-, Aktualisierungs- und Löschvorgänge), die in den letzten 24 Stunden an den Elementen in einer DynamoDB-Tabelle vorgenommen wurden. Eine Anwendung kann diese Änderungen aus dem Stream lesen und beispielsweise als Ereignisse veröffentlichen.

Das Transaktionsprotokoll-Mining hat verschiedene Vor- und Nachteile. Ein Vorteil besteht darin, dass garantiert wird, dass für jedes Update ein Ereignis veröffentlicht wird, ohne dass 2PC verwendet werden muss. Das Mining von Transaktionsprotokollen kann die Anwendung auch vereinfachen, indem die Ereignisveröffentlichung von der Geschäftslogik der Anwendung getrennt wird. Ein großer Nachteil besteht darin, dass das Format des Transaktionsprotokolls proprietär für jede Datenbank ist und sich sogar zwischen Datenbankversionen ändern kann. Außerdem kann es schwierig sein, die wichtigen Geschäftsereignisse aus den im Transaktionsprotokoll aufgezeichneten einfachen Aktualisierungen per Reverse Engineering abzuleiten.

Beim Transaktionsprotokoll-Mining ist 2PC nicht mehr erforderlich, da die Anwendung nur eine Aufgabe übernimmt: die Datenbank aktualisieren. Sehen wir uns nun einen anderen Ansatz an, der auf die Aktualisierungen verzichtet und sich ausschließlich auf Ereignisse verlässt.

Verwenden von Event Sourcing

Event Sourcing erreicht Atomizität ohne 2PC durch die Verwendung eines radikal anderen, ereigniszentrierten Ansatzes für persistente Geschäftseinheiten. Anstatt den aktuellen Status einer Entität zu speichern, speichert die Anwendung eine Abfolge von Statusänderungsereignissen. Die Anwendung rekonstruiert den aktuellen Zustand einer Entität durch Wiedergabe der Ereignisse. Immer wenn sich der Status einer Geschäftsentität ändert, wird der Ereignisliste ein neues Ereignis angehängt. Da das Speichern eines Ereignisses ein einzelner Vorgang ist, ist es von Natur aus atomar.

Um zu sehen, wie Event Sourcing funktioniert, betrachten Sie als Beispiel die Entität „Bestellung“. Bei einem herkömmlichen Ansatz wird jede Bestellung einer Zeile in einer ORDER-Tabelle und Zeilen in beispielsweise einer ORDER_LINE_ITEM-Tabelle zugeordnet. Beim Einsatz von Event Sourcing speichert der Bestelldienst eine Bestellung jedoch in Form ihrer zustandsändernden Ereignisse: Erstellt, genehmigt, versendet, storniert. Jedes Ereignis enthält genügend Daten, um den Status des Ordens zu rekonstruieren.

Erreichen Sie Atomizität in einer Microservices-Architektur mit Event Sourcing

Ereignisse werden in einem Ereignisspeicher gespeichert, bei dem es sich um eine Ereignisdatenbank handelt. Der Store verfügt über eine API zum Hinzufügen und Abrufen von Ereignissen einer Entität. Der Event Store verhält sich auch wie der Message Broker in den zuvor beschriebenen Architekturen. Es bietet eine API, die es Diensten ermöglicht, Ereignisse zu abonnieren. Der Event Store liefert allen interessierten Abonnenten alle Events. Der Event Store ist das Rückgrat einer ereignisgesteuerten Microservices-Architektur.

Eventsourcing bietet mehrere Vorteile. Es löst eines der Hauptprobleme bei der Implementierung einer ereignisgesteuerten Architektur und ermöglicht die zuverlässige Veröffentlichung von Ereignissen bei Statusänderungen. Dadurch werden Datenkonsistenzprobleme in einer Microservices-Architektur gelöst. Und weil Ereignisse und nicht Domänenobjekte persistent gespeichert werden, wird das Problem der objektrelationalen Impedanzanpassung weitgehend vermieden. Event Sourcing bietet außerdem ein 100 % zuverlässiges Prüfprotokoll der an einer Geschäftsentität vorgenommenen Änderungen und ermöglicht die Implementierung zeitlicher Abfragen, die den Status einer Entität zu jedem beliebigen Zeitpunkt bestimmen. Ein weiterer großer Vorteil von Event Sourcing besteht darin, dass Ihre Geschäftslogik aus lose gekoppelten Geschäftseinheiten besteht, die Ereignisse austauschen. Dies erleichtert die Migration von einer monolithischen Anwendung zu einer Microservices-Architektur erheblich.

Event Sourcing hat auch einige Nachteile. Es handelt sich um einen anderen und ungewohnten Programmierstil und daher ist eine Lernkurve erforderlich. Der Ereignisspeicher unterstützt nur direkt die Suche nach Geschäftsentitäten anhand des Primärschlüssels. Sie müssen Command Query Responsibility Segregation (CQRS) verwenden, um Abfragen zu implementieren. Daher müssen Anwendungen letztendlich konsistente Daten verarbeiten.

Zusammenfassung

In einer Microservices-Architektur verfügt jeder Microservice über seinen eigenen privaten Datenspeicher. Verschiedene Microservices verwenden möglicherweise unterschiedliche SQL- und NoSQL-Datenbanken. Diese Datenbankarchitektur bietet zwar erhebliche Vorteile, bringt jedoch auch einige Herausforderungen bei der verteilten Datenverwaltung mit sich. Die erste Herausforderung besteht darin, Geschäftstransaktionen so zu implementieren, dass die Konsistenz über mehrere Dienste hinweg gewahrt bleibt. Die zweite Herausforderung besteht darin, Abfragen zu implementieren, die Daten von mehreren Diensten abrufen.

Für viele Anwendungen besteht die Lösung in der Verwendung einer ereignisgesteuerten Architektur. Eine Herausforderung bei der Implementierung einer ereignisgesteuerten Architektur besteht darin, den Status atomar zu aktualisieren und Ereignisse zu veröffentlichen. Hierfür gibt es mehrere Möglichkeiten, unter anderem die Verwendung der Datenbank als Nachrichtenwarteschlange, Transaktionsprotokoll-Mining und Event Sourcing.

In zukünftigen Blogbeiträgen werden wir uns weiter mit anderen Aspekten von Microservices befassen.

Redaktion – Die siebenteilige Artikelserie ist nun komplett:

  1. Einführung in Microservices
  2. Erstellen von Microservices: Verwenden eines API-Gateways
  3. Erstellen von Microservices: Interprozesskommunikation in einer Microservices-Architektur
  4. Service Discovery in einer Microservices-Architektur
  5. Ereignisgesteuertes Datenmanagement für Microservices (dieser Artikel)
  6. Auswählen einer Bereitstellungsstrategie für Microservices
  7. Refactoring eines Monolithen in Microservices

Sie können den kompletten Artikelsatz sowie Informationen zur Implementierung von Microservices mit NGINX Plus auch als E-Book herunterladen – Microservices: Vom Entwurf bis zur Bereitstellung . Und sehen Sie sich unsere Serie zur Microservices-Referenzarchitektur und die Seite mit Microservices-Lösungen an.

Gastblogger Chris Richardson ist der Gründer des ursprünglichen CloudFoundry.com , einer frühen Java PaaS (Platform as a Service) für Amazon EC2. Heute berät er Organisationen bei der Verbesserung der Entwicklung und Bereitstellung von Anwendungen. Unter http://microservices.io bloggt er außerdem regelmäßig über Microservices.


„Dieser Blogbeitrag kann auf Produkte verweisen, die nicht mehr verfügbar und/oder nicht mehr unterstützt werden. Die aktuellsten Informationen zu verfügbaren F5 NGINX-Produkten und -Lösungen finden Sie in unserer NGINX-Produktfamilie . NGINX ist jetzt Teil von F5. Alle vorherigen NGINX.com-Links werden auf ähnliche NGINX-Inhalte auf F5.com umgeleitet."