top of page
Cerca

Command Query Responsibility Segregation pattern

  • Immagine del redattore: Gregorat Paolo
    Gregorat Paolo
  • 8 giu 2016
  • Tempo di lettura: 4 min

In questo articolo presentiamo una panoramica introduttiva all’argomento CQRS. Il pattern architetturale Command Query Responsibility Segregation (CQRS), di cui sempre più si stanno apprezzando i vantaggi e le possibilità. CQRS parte da un’idea apparentemente semplice, ma è capace di profondo impatto sul modo in cui progettiamo e sviluppiamo le nostre applicazioni. Cominciamo con una introduzione panoramica su CQRS,

Introduzione

Command Query Responsibility Segregation (CQRS) è un pattern concettualmente molto semplice, ma che può condurre verso profondi e interessanti sviluppi nel design di sistemi informativi. In questo primo articolo verranno spiegati i concetti fondamentali, senza alcun riferimento a una tecnologia particolare



Una nuova idea di web application

L’idea tradizionale che le persone (siano essi utilizzatori finali o progettisti o sviluppatori) hanno di web application è quello di considerarla sostanzialmente come un datastore CRUD. Lo schema mentale è quello di una struttura di record in cui è possibile crearli, leggerli, aggiornarli ed eliminarli (Create, Read, Update, Delete). Nel caso più semplice quindi, le interazioni sono tutte di memorizzazione e recupero di record.

Mano a mano che i business requirements di un progetto diventano sempre più sofisticati, ci si allontana progressivamente da tale modello. Spesso si ha la necessità di mostrare i dati in maniera diversa dalla semplice struttura prevista per i record, per esempio raggruppare più record in uno solo oppure creare record virtuali combinando dati provenienti da fonti diverse. Per quanto riguarda l’update, invece, spesso è necessario introdurre delle regole di validazione che consentono di salvare solo determinate combinazioni di dati oppure dedurre quelli da salvare da quelli visualizzati (che possono essere diversi). Quando si presentano questi casi ci si trova di fronte a rappresentazioni multiple delle stesse informazioni.

Gli utenti quindi interagiscono con diversi modi di presentare le informazioni del sistema, mentre invece gli analisti/sviluppatori costruiscono il proprio modello concettuale (Domain Model) che descrive le varie entità che fanno parte di un sistema e le relazioni che intercorrono fra di loro. E normalmente anche la parte di persistenza si avvicina quanto più possibile al modello concettuale.

Figura 1 – Lo schema descrittivo di una applicazione web 3-tier basata su un’architettura “classica” CRUD.

Una struttura avente strati multipli di presentazione dei dati può sembrare piuttosto complicata, ma a livello più basso esiste comunque una singola rappresentazione concettuale che funge da punto di integrazione fra tutte le diverse presentazioni.

Un paradigma diverso: separare aggiornamento e visualizzazione

L’architettura presentata da Martin Fowler e denominata, appunto Command Query Responsibility Segregation si basa su un concetto apparentemente semplice: il cambiamento che CQRS introduce è quello di dividere il modello concettuale in modelli separati per l’aggiornamento e la visualizzazione, a cui ci si riferisce, rispettivamente, con i nomi di Command e Query. Tali nomi sono derivati dal concetto di Command Query Separation, termine coniato da Bertrand Mayer . L’idea di base di questo concetto è quella di dividere i metodi di un oggetto in due categorie nettamente separate:

  • Queries: a questa categoria appartengono i metodi che restituiscono un risultato e non cambiano lo stato osservabile del sistema (non introducono quindi side effects).

  • Commands: in questa categoria ricadono quelli che cambiano lo stato del sistema, ma non restituiscono un valore di ritorno.

Il motivo di questa separazione è che per molti problemi, in particolare nei casi con domini più complessi, l’utilizzo di un unico modello concettuale per commands and queries fa aumentare le complicazioni e contemporaneamente diminuire i vantaggi.


Modelli separati in concreto

Per modelli separati intendiamo object models diversi, che possono essere eseguiti in processi logici differenti e anche su hardware separati. Nell’ambito di una web application questa situazione si traduce nel seguente modo: il rendering di una pagina web richiesta da un utente coinvolge il query model, mentre invece una operazione di modifica di dati coinvolge il command model e il risultato viene successivamente comunicato al query model, il quale provvede a renderizzare la pagina coerentemente al cambiamento di stato. I due modelli possono condividere lo stesso database: in questo caso esso funge da mezzo di comunicazione fra i due. Oppure ciascuno dei due modelli può usare un proprio database: e in questo caso invece bisogna implementare anche un meccanismo di comunicazione tra i due modelli. I due modelli non devono per forza essere costituiti da oggetti diversi: possono avere anche gli stessi oggetti ma con differenti interfacce lato query e lato command. Ma la definizione pura di CQRS prevede modelli nettamente separati.




Figura 2 – Raffigurazione concettuale d’insieme di una applicazione web 3-tier basata sul pattern architetturale CQRS.

Relazione tra CQRS ed altri pattern architetturali

Abbiamo visto in breve i concetti base di CQRS: un’idea dagli effetti decisivi sulla progettazione delle web application può in effetti anche basarsi su principi sostanzialmente semplici. Ma in che modo questa piccola “rivoluzione” si integra con quello che già c’è? In realtà, Command Query Responsibility Segregation si sposa perfettamente ad altri pattern architetturali.


Task-Based User Interfaces

Quanto più ci si allontana dal modello a rappresentazione singola dei dati con cui si interagisce tramite CRUD, tanto più facile risulta orientarsi verso l’implementazione di task-based user interfaces


Event Sourcing

L’interazione con il command model inevitabilmente conduce all’Event Sourcing (ES). ES è un pattern architetturale che permette di rappresentare gli oggetti come una sequenza di eventi che si è verificata nel tempo e che li ha portati ad essere nel loro stato attuale. Tutti i cambiamenti di stato dell’applicazione vengono quindi conservati ed è quindi sempre possibile recuperarli e ricostruire la storia passata degli oggetti ed eventualmente usarla come base per adattare automaticamente uno stato a far fronte a cambiamenti retroattivi.


Eager Read Derivation

In molti casi la maggior parte di domain logic è necessaria in fase di update: quindi ha senso ricorrere al concetto di Eager Read Derivation per semplificare il query model. Questo aspetto verrà approfondito nel prossimo articolo.


Domain Driven Design

CQRS è particolarmente adatto ai domini complessi, soprattutto quelli che traggono beneficio anche dall’adozione di un approccio di tipo Domain-Driven Design

EndFragment

Post recenti

Mostra tutti

2016 dott. Paolo Gregorat

  • Facebook Clean Grey
  • LinkedIn Clean Grey
bottom of page