Penso che sia importante tenere presente che la differenza principale tra Command
e Event
è semantica .
Hohpe :
Messages are ultimately just bundles of data, but the sender can have different intentions for what it expects the receiver to do with the message. It can send a Command Message specifying a function or method on the receiver that the sender wishes to invoke.... it can send an Event Message, notifying the receiver of a change in the sender.
CommandReceived
è un evento ; handleEvent
è un comando .
Una distinzione chiave tra i due è questa
I comandi - spostano verso l'autorizzazione per un determinato stato
- gli eventi viaggiano lontano dall'autorità per un determinato stato
Con questo in mente, diamo un'occhiata ai giocatori
Aggregati sono un componente del modello di dominio, responsabile di garantire che le modifiche allo stato del dominio soddisfino l'invarianza di business. La ragione del modello di dominio per esistere è quella di essere l'autorità per quello stato. Quindi ci aspetteremmo che i messaggi percepiscano il modello di dominio (e quindi, in forma aggregata) come comandi .
I gestori dei processi non interagiscono direttamente con lo stato del dominio direttamente. Sono componenti di orchestrazione che reagiscono ai messaggi di altre autorità. Quindi dovremmo aspettarci che questi messaggi in arrivo siano eventi . Nel reagire a questi messaggi, i process manager di solito inviano messaggi a modelli di dominio (o altre strutture, come gateway di posta elettronica). Questi messaggi in uscita sarebbero comandi .
Which negative consequences would an aggregate have, that directly consumes events produced by another aggregate?
"direttamente" può significare molte cose diverse qui. Concettualmente, non c'è niente di sbagliato in un comando come
void placeOrder( OrderFormSubmitted event )
Dove le cose si fanno interessanti è capire se includere o meno messaggi diversi all'interno della stessa transazione . La discussione di eventi di dominio di Udi Dahan utilizza gestori di eventi che vengono eseguiti nello stesso thread / stessa transazione di il comando iniziale; così l'intera orchestrazione avrà successo o fallirà insieme.
Inoltre, poiché vuoi davvero evitare il commit a due fasi se puoi eventualmente aiutarlo, devi davvero essere sicuro che tutti gli aggregati coinvolti nell'orchestrazione possano partecipare alla stessa transazione (cioè: sono memorizzati nel stesso database).
Gli scritti più recenti tendono ad assumere che gli aggregati possano essere distribuiti, nel qual caso vuoi veramente separare le transazioni.
In genere, se si sta eseguendo un'orchestrazione su più contesti limitati, si vorranno comunque transazioni separate.
Un ulteriore problema con la gestione degli eventi "direttamente" impedisce alle modifiche ai messaggi di forzare un aggiornamento a catena sul sistema. Il controllo delle versioni di un evento in un sistema basato su eventi di Greg Young è un'ottima lettura, ma il riepilogo di alto livello è che gli eventi sono messaggi dal vecchio modello al nuovo, quindi dovresti investire il capitale iniziale del design per assicurarti che lo schema dei messaggi sia progettato con il supporto change in mente.