Microsoft Orleans

Orleans ist ein plattformübergreifendes Framework zum Erstellen stabiler und skalierbarer verteilter Anwendungen. Verteilte Anwendungen werden als Apps definiert, die sich über mehr als einen einzelnen Prozess erstrecken, und oft über Hardwaregrenzen hinweg Peer-zu-Peer-Kommunikation verwenden. Orleans ist von einem einzelnen lokalen Server bis zu mehreren hunderttausend verteilten, hoch verfügbaren Anwendungen in der Cloud skalierbar. Orleans erweitert bekannte Konzepte und C#-Ausdrücke für Umgebungen mit mehreren Servern. Orleans ist für die elastische Skalierung konzipiert. Tritt ein Host einem Cluster bei, kann er neue Aktivierungen akzeptieren. Verlässt ein Host den Cluster (aufgrund eines Herunterskalierens oder eines Computerfehlers) werden die Aktivierungen für diesen Host bei Bedarf auf den verbleibenden Hosts reaktiviert. Ein Orleans-Cluster kann auf einen einzelnen Host herunterskaliert werden. Dieselben Eigenschaften, auf denen die elastische Skalierbarkeit basiert, ermöglichen auch die Fehlertoleranz. Der Cluster erkennt Fehler automatisch und führt eine schnelle Wiederherstellung durch.

Eines der wichtigsten Entwurfsziele von Orleans ist die Vereinfachung der komplexen Entwicklung verteilter Anwendungen durch die Bereitstellung gemeinsamer Muster und APIs. Mit Orleans können Entwickler*innen, die mit der Entwicklung von Einzelserveranwendungen vertraut sind, problemlos resiliente und skalierbare cloudnative Dienste und andere verteilte Anwendungen erstellen. Aus diesem Grund wird Orleans häufig als „Verteiltes .NET-Framework“ bezeichnet und ist die beste Option für die Erstellung cloudnativer Apps. Orleans kann überall dort ausgeführt werden, wo .NET unterstützt wird. Dies schließt das Hosting in Linux, Windows und macOS ein. Orleans-Apps können in Kubernetes, auf virtuellen Computern und in PaaS-Diensten wie Azure App Service und Azure Container Apps bereitgestellt werden.

Das Aktorenmodell

Orleans basiert auf dem sogenannten „Aktorenmodell“. Das Aktorenmodell stammt aus den frühen 1970er-Jahren und stellt eine Kernkomponente von Orleans dar. Das Aktorenmodell ist ein Programmiermodell, bei dem jeder Aktor ein einfaches, nebenläufiges und unveränderliches Objekt darstellt, das über einen Zustand und das entsprechende Verhalten verfügt. Aktoren kommunizieren miteinander ausschließlich über asynchrone Nachrichten. In Orleans wurde insbesondere die Abstraktion des virtuellen Aktors eingeführt, bei der Aktoren dauerhaft existieren.

Hinweis

Aktoren sind rein logische Entitäten, die immer virtuell vorhanden sind. Ein Aktor kann nicht explizit erstellt oder zerstört werden, weshalb der Ausfall eines Servers, auf dem er ausgeführt wird, keinen Einfluss auf seine virtuelle Existenz hat. Da Aktoren immer vorhanden sind, sind sie immer adressierbar.

Dieser Ansatz für die Erstellung einer neuen Generation verteilter Anwendungen ist im Zeitalter der Cloud neuartig. Das Orleans-Programmiermodell macht die Komplexität paralleler, in hohem Maße verteilter Anwendungen beherrschbar, ohne deren Funktionen oder die Möglichkeiten von Entwickler*innen einzuschränken.

Weitere Informationen finden Sie über Microsoft Research unter Orleans: Virtual Actors (Virtuelle Aktoren). Ein virtueller Aktor wird als Orleans-Grain dargestellt.

Was sind Grains?

Grains gehören zu den Orleans-Primitiven. In Bezug auf das Aktorenmodell sind Grains virtuelle Aktoren. Der Grundbaustein jeder Orleans-Anwendung sind Grains. Grains sind Entitäten mit benutzerdefinierter Identität, benutzerdefiniertem Verhalten und benutzerdefiniertem Zustand. Dies wird in der folgenden Abbildung visuell dargestellt:

Grains besitzen eine stabile Identität, stabiles Verhalten und einen stabilen Zustand

Grainidentitäten sind benutzerdefinierte Schlüssel, mit denen Grains immer für Aufrufe verfügbar sind. Grains können von anderen Grains oder von einer beliebigen Anzahl externer Clients aufgerufen werden. Jedes Grain ist eine Instanz einer Klasse, die mindestens eine der folgenden Schnittstellen implementiert:

Grains können Daten in flüchtigem oder dauerhaftem Zustand aufweisen, die in jedem Speichersystem gespeichert werden können. Daher partitionieren Grains implizit Anwendungszustände und ermöglichen so eine automatische Skalierbarkeit und eine vereinfachte Wiederherstellung nach Fehlern. Der Grainzustand wird im Arbeitsspeicher beibehalten, während das Grain aktiv ist, was zu einer niedrigeren Latenz und geringeren Auslastung der Datenspeicher führt.

Verwalteter Lebenszyklus von Orleans-Grains

Die Orleans-Laufzeit instanziiert Grains automatisch bei Bedarf. Längere Zeit nicht verwendete Grains werden automatisch aus dem Arbeitsspeicher entfernt, um Ressourcen freizugeben. Aufgrund ihrer stabilen Identität können Grains, unabhängig davon, ob sie bereits in den Arbeitsspeicher geladen wurden oder nicht, aufgerufen werden. Dies ermöglicht auch eine transparente Wiederherstellung nach einem Fehler, da der Aufrufer zu keinem Zeitpunkt wissen muss, auf welchem Server Grains instanziiert werden. Grains verfügen über einen verwalteten Lebenszyklus. Dabei ist die Orleans-Laufzeit für das Aktivieren/Deaktivieren und das Platzieren/Auffinden von Grains nach Bedarf verantwortlich. Dadurch können Entwickler*innen Code so schreiben, als ob sich alle Grains jederzeit im Arbeitsspeicher befinden.

Was sind Silos?

Silos sind ein weiteres Beispiel für Orleans-Primitiven. In einem Silo werden ein oder mehrere Grains gehostet. Die Orleans-Laufzeit implementiert das Programmiermodell für Anwendungen.

In der Regel wird eine Gruppe von Silos aus Gründen der Skalierbarkeit und Fehlertoleranz als Cluster ausgeführt. Bei der Ausführung als Cluster werden Silos zur Verteilung der Arbeit, zur Ermittlung von Fehlern und zur Wiederherstellung koordiniert. Mithilfe der Laufzeit können Grains, die im Cluster gehostet werden, so kommunizieren, als ob sie sich in einem einzelnen Prozess befinden. Im folgenden Diagramm wird die Beziehung zwischen Clustern, Silos und Grains visualisiert:

Ein Cluster mit einem oder mehreren Silos, ein Silo mit einem oder mehreren Grains

Das obige Diagramm zeigt die Beziehung zwischen Clustern, Silos und Grains. Die Anzahl von Clustern ist nicht begrenzt, wobei jeder Cluster über ein oder mehrere Silos verfügt und jedes Silo über einen oder mehrere Grains.

Zusätzlich zum Kernprogrammiermodell stellen Silos eine Reihe von Laufzeitdiensten wie Timer, Erinnerungen (dauerhafte Timer), Persistenz, Transaktionen oder Streams für Grains bereit. Weitere Informationen finden Sie unter Verwendungsmöglichkeiten für Orleans.

Web-Apps und andere externe Clients rufen Grains im Cluster mithilfe der Clientbibliothek auf, die automatisch die Netzwerkkommunikation verwaltet. Clients können aus Gründen der Einfachheit auch mit Silos zusammen im gleichen Prozess gehostet werden.

Verwendungsmöglichkeiten für Orleans

Orleans ist ein Framework zur Erstellung cloudnativer Apps und eignet sich besonders für .NET-Apps, die später skaliert werden müssen. Die Möglichkeiten für die Verwendung von Orleans sind vielfältig – zu den gängigsten Einsatzmöglichkeiten zählen z. B. Gaming, Bankgeschäfte, Chat-Apps, GPS-Tracking, Aktienhandel, Warenkörbe oder Abstimmungs-Apps. Orleans wird von Microsoft in Azure, Xbox, Skype, Halo, PlayFab, Gears of War und vielen weiteren internen Diensten verwendet. Orleans verfügt über viele Features, die eine einfache Verwendung in unterschiedlichen Anwendungen ermöglichen.

Persistenz

Orleans bietet ein einfaches Persistenzmodell, das vor der Verarbeitung einer Anforderung die Verfügbarkeit des Zustands und die Beibehaltung der Konsistenz sicherstellt. Grains können über mehrere benannte persistente Datenobjekte verfügen. So kann ein Objekt für ein Benutzerprofil z. B. „Profil“ heißen und ein Bestandsobjekt „Bestand“. Dieser Zustand kann in jedem Speichersystem gespeichert werden.

Während der Ausführung eines Grains wird sein Zustand im Arbeitsspeicher beibehalten, sodass Leseanforderungen ohne Zugriff auf den Speicher verarbeitet werden können. Wird der Zustand aktualisiert, können Sie durch Aufrufen von IStorage.WriteStateAsync sicherstellen, dass der Sicherungsspeicher im Sinne der Dauerhaftigkeit und Konsistenz aktualisiert wird.

Weitere Informationen finden Sie unter Aggregationsintervall-Persistenz.

Timer und Erinnerungen

Erinnerungen sind ein dauerhafter Planungsmechanismus für Grains. Damit können Sie sicherstellen, dass eine Aktion zu einem späteren Zeitpunkt ausgeführt wird, selbst wenn das Grain dann gar nicht aktiviert ist. Timer sind die nicht dauerhafte Entsprechung zu Erinnerungen, die für häufige Ereignisse verwendet werden können, die keine Zuverlässigkeit erfordern.

Weitere Informationen finden Sie unter Timer und Erinnerungen.

Flexible Grainplatzierung

Wird ein Grain in Orleans aktiviert, entscheidet die Laufzeit, auf welchem Server (Silo) dies geschehen soll. Dies wird als Grainplatzierungbezeichnet.

Der Platzierungsprozess ist in Orleans vollständig konfigurierbar. Entwickler*innen können aus einer Reihe von vorgefertigten Richtlinien für die Platzierung auswählen, z. B. „random“ (zufällig), „prefer-local“ (lokal bevorzugen) und „load-based“ (auslastungsbasiert), oder eine benutzerdefinierte Logik festlegen. Dies ermöglicht volle Flexibilität bei der Entscheidung, wo Grain erstellt wird. So können Grains z. B. auf einem Server in der Nähe von Ressourcen, mit denen sie arbeiten müssen, oder von anderen Grains, mit denen sie kommunizieren, platziert werden.

Weitere Informationen finden Sie unter Grainplatzierung.

Grainversionsverwaltung und heterogene Cluster

Es kann eine Herausforderung darstellen, Produktionssysteme so zu aktualisieren, dass Änderungen sicher erfasst werden, insbesondere bei zustandsbehafteten Systemen. Aus diesem Grund können Grainschnittstellen in Orleans mit Versionsangabe versehen werden.

Der Cluster verwaltet eine Zuordnung der verfügbaren Grainimplementierungen auf den Silos im Cluster sowie die Versionen dieser Implementierungen. Diese Versionsangabe wird von der Laufzeit in Verbindung mit Platzierungsstrategien verwendet, um beim Weiterleiten von Aufrufen an Grains Platzierungsentscheidungen zu treffen. Darüber hinaus können so für die sichere Aktualisierung von Grains mit Versionsangabe auch heterogene Cluster erzielt werden, bei denen Silos unterschiedliche Grainimplementierungen verfügbar machen.

Weitere Informationen finden Sie unter Grainversionsverwaltung.

Zustandslose Worker

Zustandslose Worker sind speziell markierte Grains, denen kein Zustand zugeordnet ist und die in mehreren Silos gleichzeitig aktiviert werden können. Dies erhöht den Grad der Parallelität für zustandslose Funktionen.

Weitere Informationen finden Sie unter Zustandslose Workergrains.

Filter für Grainaufrufe

Ein Filter für Grainaufrufe ist eine bei vielen Grains übliche Logik. Orleans unterstützt Filter für eingehende und ausgehende Anrufe. Häufig dienen Filter der Autorisierung, Protokollierung und Telemetrie sowie der Fehlerbehandlung.

Anforderungskontext

Metadaten und andere Informationen können mithilfe des Anforderungskontexts mit einer Reihe von Anforderungen übergeben werden. Der Anforderungskontext kann zum Speichern von Informationen für die verteilte Ablaufverfolgung oder von anderen benutzerdefinierten Werten verwendet werden.

Verteilte ACID-Transaktionen

Neben dem oben beschriebenen einfachen Persistenzmodell können Grains auch einen Transaktionszustand aufweisen. Mehrere Grains können zusammen an ACID-Transaktionen teilnehmen, unabhängig vom endgültigen Speicherort ihres Zustands. Transaktionen in Orleans sind verteilt und dezentralisiert (d. h. es gibt keinen zentralen Transaktions-Manager oder -Koordinator), und sie verfügen über serialisierbare Isolation.

Weitere Informationen zu Transaktionen finden Sie unter Transaktionen.

Datenströme

Mithilfe von Streams können Entwickler*innen eine Reihe von Datenelementen nahezu in Echtzeit verarbeiten. Orleans-Streams werden verwaltet. Sie müssen erst erstellt oder registriert werden, wenn ein Grain oder Client einen Stream veröffentlicht oder abonniert. Dadurch können Streamproducer und Streamconsumer stärker voneinander und von der Infrastruktur getrennt werden.

Die Streamverarbeitung ist zuverlässig: Grains können Prüfpunkte (Cursor) speichern und während der Aktivierung oder zu einem späteren Zeitpunkt auf einen gespeicherten Prüfpunkt zurücksetzen. Streams unterstützen die Batchübermittlung von Nachrichten an Consumer, um die Effizienz und Wiederherstellungsleistung zu verbessern.

Streams werden durch Dienste in der Warteschlange unterstützt, z. B. Azure Event Hubs oder Amazon Kinesis.

Eine beliebige Anzahl von Streams kann in eine kleinere Anzahl von Warteschlangen mithilfe von Multiplex gebündelt werden, um die Verantwortung für die Verarbeitung dieser Warteschlangen gleichmäßig über den Cluster zu verteilen.

Einführungsvideo zu Orleans

Eine Videoeinführung in Orleans finden Sie im folgenden Video:

Nächste Schritte