Come posso evitare una transazione di aggregazione incrociata?

6

Considera questo esempio semplificato: in un sito web di vendita di biglietti online, i biglietti hanno prezzi variabili che cambiano nel tempo.

L'utente cerca i biglietti . Una volta che trova un biglietto che desidera, fa clic su "Acquista" e quindi viene emessa una offerta . Le quotazioni sono persistenti e hanno il proprio localizzatore che viene inviato per e-mail. La pagina di quotazione si apre, mostrando la ripartizione di ciò che sta per pagare e un pulsante da pagare. A questo punto, il biglietto è ancora disponibile per gli altri. Se l'utente fa clic su "Paga ora", viene avviato un processo di pagamento e viene emesso un ordine d'acquisto con i suoi dettagli.

Quando viene pagato un ordine d'acquisto, lo stato dell'offerta deve essere impostato come "Accettato" e fare riferimento all'ordine d'acquisto; lo stato del ticket è impostato come "Venduto".

Come da requisiti, ciò deve avvenire in modo atomico, il che significa che non è accettabile avere un ordine di acquisto a pagamento che fa riferimento a un preventivo non accettato o un biglietto non venduto in un dato momento. In sostanza, la coerenza finale non è consentita.

Ci sono due grandi aggregati, Quote e PurchaseOrder . Il primo gestisce il calcolo della ripartizione, le tasse, ecc ... Il secondo gestisce i dettagli del pagamento per un preventivo, l'aumento di eventi di pagamento, ecc ... Il problema che ho è che adesso sembra che devo usare una transazione attraverso il biglietto, citazione e ordine d'acquisto quando l'ultimo è pagato.

Come posso modellare questo onorando la regola "Le transazioni non devono superare i limiti aggregati?"

    
posta NullOrEmpty 27.06.2017 - 23:49
fonte

1 risposta

6

Hai bisogno di un process manager / saga che faccia esattamente ciò di cui hai bisogno senza utilizzare la transazione che genera più aggregati.

Sostanzialmente Saga vorrebbe reserve del ticket immediatamente prima dell'avvio del pagamento e vorrebbe markTicketAsSold dopo che il pagamento è andato a buon fine o releaseTheReservation dopo che il pagamento è fallito.

Questo processo e l'invariante che un reserved o sold ticket non può essere reserved di nuovo garantirebbe che il sistema come un buco sia nello stato corretto in ogni momento.

As per requirements, this must happen in an atomic fashion, meaning that it is not acceptable to have a paid purchase order referencing a non accepted quote, or a non sold ticket at any given time. Essentially, eventual consistency is not allowed.

Questo non sembra essere un invariante valido. L'invariante dovrebbe essere "un biglietto venduto non può essere rivenduto". Definire con cura gli invarianti di business ti aiuterà a progettare i confini aggregati e a modellare correttamente i processi a lungo termine.

    
risposta data 28.06.2017 - 08:01
fonte

Leggi altre domande sui tag