Zum Beispiel, wenn Sie ein Register Formular abgesendet hat , müssen Sie in der überprüfen Domain Model
( WriteModel
in CQRS
) , dass es in einem gültigen Zustand (zB E - Mail - Adresse Syntax, Alter, etc.) ist.
Dann erstellen Sie eine Command
und senden sie an eine Command Bus
.
Ich verstehe, dass Befehle nichts zurückgeben sollten.
Wie gehen Sie mit einem Fehler darüber hinaus um Command Bus
? (Beispiel: Ein Benutzer hat sich 1 Sekunde zuvor bei demselben registriert username/email
.)
Woher wissen Sie, dass dieser Befehl fehlgeschlagen ist, und woher wissen Sie, dass der Fehler aufgetreten ist?
Antworten:
Das ist eine Ansicht, aber nicht ganz in Stein gemeißelt. Erwägen Sie Schreibvorgänge (PUT, POST, DELETE) in HTTP. Alle diese Nachrichten sind Befehle in dem Sinne, dass es sich um Nachrichten handelt, die den Status der Ressourcenänderung anfordern, und dennoch alle Antworten zurückgeben.
In einem Fall, in dem Sie direkt mit dem Befehlshandler kommunizieren, ist eine zurückgegebene Nachricht eine sehr vernünftige Methode, um zu bestätigen, dass der Befehl empfangen und verarbeitet wurde.
Wenn Sie eine Middleware wie einen Bus verwenden, die Sie daran hindert, direkt mit dem Ziel zu kommunizieren, sollten Sie asynchrone Messaging-Muster verwenden Anrufer?
Eine Idee ist, das Ergebnis des Befehls zu abonnieren. Dies basiert auf einigen Ideen in Hohpes Enterprise Integration Patterns. Die Grundidee ist, dass der Client, da er mit der gesendeten Befehlsnachricht vertraut ist, gut positioniert ist, um alle neuen Nachrichten zu abonnieren, die als Folge der Befehlsnachricht veröffentlicht wurden. Nachdem die Daten im Protokoll gespeichert wurden, veröffentlicht der Befehlshandler Ereignisse, die den Erfolg der Änderung anzeigen, und der Client abonniert diese Ereignisse. Er erkennt die richtigen Ereignisse, indem er die Übereinstimmung verschiedener Kennungen in der Nachricht berücksichtigt (Ursachen-ID, Korrelations-ID usw.).
Alternative Ansätze sind etwas direkter. Eine Möglichkeit wäre, einen Rückruf in die Nachricht aufzunehmen, der vom Befehlshandler aufgerufen werden kann, nachdem die Nachricht erfolgreich verarbeitet wurde.
Eine sehr ähnliche Alternative besteht darin, Platz in der Befehlsnachricht für den Befehlshandler zu reservieren, um die Bestätigung zu schreiben - da der Client die fragliche Befehlsnachricht bereits hat, ist die Schaltung bereits abgeschlossen. Denken Sie an " Versprechen " oder " abschließbare Zukunft". Die Nachricht teilt dem Befehlshandler mit, wo die Bestätigung geschrieben werden soll. dies signalisiert dem Client (Countdown-Latch), dass die Bestätigung verfügbar ist.
Und natürlich haben Sie die zusätzliche Möglichkeit, die Middleware zu entfernen, die Sie scheinbar daran hindert, einfach das Richtige zu tun.
Wenn Sie die Benutzerregistrierung idempotent handhaben, ist dies nicht unbedingt ein Fehler. Das Wiederholen von Nachrichten, bis eine Antwort beobachtet wird, ist eine übliche Methode, um mindestens eine Zustellung sicherzustellen.
quelle
Es gibt viele Arten der Validierung. Die Überprüfung bei der Überprüfung der E-Mail-Adressensyntax und des Altersformats ist eine Art der Überprüfung, die ein Befehl durchführen kann. Dies ist kein wirkliches Domain-Problem. Es mag so aussehen, weil einige Domain-Experten Ihnen diese Spezifikationen mitteilen würden, aber Sie sollten diese Art der Validierung bei der Befehlserstellung durchführen. Tatsächlich besteht die allgemeine Idee darin, die Validierung so bald wie möglich durchzuführen, da es nach dem Erstellen eines Befehls und dem Senden an einen BUS komplizierter ist, Maßnahmen zu ergreifen.
Diese Art der Validierung wird in der CQRS-Community seit Beginn von CQRS viel diskutiert. Wo kann man es machen? Es ist sehr umstritten. Ich persönlich gehe folgendermaßen vor: Bevor der Befehl an den BUS gesendet wird, markiere ich den Benutzernamen / die E-Mail als zentralisiert (dh eine eindeutige Indexbeschränkung für den Benutzernamen / die E-Mail). Danach sende ich den Befehl. Der Nachteil ist, dass, wenn der Befehl fehlschlägt, der Benutzername für einen kurzen Zeitraum vergeben und nicht verwendet wird. Dies ist akzeptabel für mein Geschäft, wahrscheinlich für Ihr Geschäft.
Wenn ein asynchroner Befehl vom Aggregat aufgrund einer Domäneninvariante zurückgewiesen wird, müssen einige Maßnahmen ergriffen werden, indem ein Ausgleichsbefehl ausgegeben wird, der den Herausgeber des Befehls auf irgendeine Weise benachrichtigt (dh eine Erklärungs-E-Mail sendet, dass der Befehl fehlgeschlagen ist).
Das Problem bei doppelten E-Mails ist, dass Sie keine E-Mails senden können, da diese E-Mail-Adresse einer anderen Person gehört. Deshalb überprüfe ich sie, bevor ich den Befehl an den Bus sende.
quelle
Die Validierung sollte in einem Dekorateur durchgeführt werden. Dann könnte jeder Befehl, der eine Validierung benötigt, als solcher dekoriert werden.
Validierungen können mit Ausnahmen behandelt werden, wenn Ihre Rückgabe mit Ihrem Befehl ungültig wird, sodass sie entweder mit Synchronisierungs- oder Asynchronisierungsaufrufen mit dem zurückgegebenen Aufgabenergebnis abgerufen werden können.
Eine andere Möglichkeit besteht darin, sich die Validierung als eine Art "Abfrage" vorzustellen, die ein Validierungsergebnis zurückgibt. Führen Sie die Überprüfungsabfrage aus, und führen Sie dann den Befehl aus, wenn Sie übergeben werden. Dies wäre eine Alternative zum Dekorateuransatz.
quelle