add README.md, cqrs.ucls and etc/cqrs.urm.puml
This commit is contained in:
parent
5873aeeb69
commit
c744bf418a
@ -0,0 +1,29 @@
|
|||||||
|
---
|
||||||
|
layout: pattern
|
||||||
|
title: CQRS
|
||||||
|
folder: cqrs
|
||||||
|
permalink: /patterns/cqrs/
|
||||||
|
pumlid:
|
||||||
|
categories: Architectural
|
||||||
|
tags:
|
||||||
|
- Java
|
||||||
|
- Difficulty-Intermediate
|
||||||
|
---
|
||||||
|
|
||||||
|
## Intent
|
||||||
|
CQRS Command Query Responsibility Segregation - Seperate the query side from the command side.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
## Applicability
|
||||||
|
Use the CQRS pattern when
|
||||||
|
|
||||||
|
* you want to scale the queries and commands independently.
|
||||||
|
* you want to use different data models for queries and commands. Useful when dealing with complex domains.
|
||||||
|
* you want to use architectures like event sourcing or task based UI.
|
||||||
|
|
||||||
|
## Credits
|
||||||
|
|
||||||
|
* [Greg Young - CQRS, Task Based UIs, Event Sourcing agh!](http://www.amazon.com/Effective-Java-Edition-Joshua-Bloch/dp/0321356683)
|
||||||
|
* [Martin Fowler - CQRS](http://codebetter.com/gregyoung/2010/02/16/cqrs-task-based-uis-event-sourcing-agh/)
|
||||||
|
* [Oliver Wolf - CQRS for Great Good](https://www.youtube.com/watch?v=Ge53swja9Dw)
|
BIN
cqrs/etc/cqrs.png
Normal file
BIN
cqrs/etc/cqrs.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 103 KiB |
@ -1,6 +1,111 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<class-diagram version="1.2.0" icons="true" always-add-relationships="false" generalizations="true" realizations="true"
|
<class-diagram version="1.2.0" icons="true" always-add-relationships="false" generalizations="true" realizations="true"
|
||||||
associations="true" dependencies="true" nesting-relationships="true" router="FAN">
|
associations="true" dependencies="false" nesting-relationships="true" router="FAN">
|
||||||
|
<interface id="1" language="java" name="com.iluwatar.cqrs.commandes.ICommandService" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/commandes/ICommandService.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="-1" width="-1" x="291" y="-49"/>
|
||||||
|
<display autosize="true" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</interface>
|
||||||
|
<class id="2" language="java" name="com.iluwatar.cqrs.commandes.CommandServiceImpl" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/commandes/CommandServiceImpl.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="263" width="256" x="170" y="87"/>
|
||||||
|
<display autosize="false" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</class>
|
||||||
|
<interface id="3" language="java" name="com.iluwatar.cqrs.queries.IQueryService" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/queries/IQueryService.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="182" width="248" x="176" y="428"/>
|
||||||
|
<display autosize="false" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</interface>
|
||||||
|
<class id="4" language="java" name="com.iluwatar.cqrs.queries.QueryServiceImpl" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/queries/QueryServiceImpl.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="258" width="253" x="169" y="665"/>
|
||||||
|
<display autosize="false" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</class>
|
||||||
|
<class id="5" language="java" name="com.iluwatar.cqrs.domain.model.Book" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/domain/model/Book.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="326" width="158" x="778" y="-93"/>
|
||||||
|
<display autosize="false" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</class>
|
||||||
|
<class id="6" language="java" name="com.iluwatar.cqrs.dto.Book" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/dto/Book.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="219" width="150" x="541" y="607"/>
|
||||||
|
<display autosize="false" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</class>
|
||||||
|
<class id="7" language="java" name="com.iluwatar.cqrs.domain.model.Author" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/domain/model/Author.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="-1" width="-1" x="608" y="70"/>
|
||||||
|
<display autosize="true" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</class>
|
||||||
|
<class id="8" language="java" name="com.iluwatar.cqrs.dto.Author" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/dto/Author.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="-1" width="-1" x="834" y="719"/>
|
||||||
|
<display autosize="true" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</class>
|
||||||
|
<class id="9" language="java" name="com.iluwatar.cqrs.util.HibernateUtil" project="cqrs"
|
||||||
|
file="/cqrs/src/main/java/com/iluwatar/cqrs/util/HibernateUtil.java" binary="false" corner="BOTTOM_RIGHT">
|
||||||
|
<position height="-1" width="-1" x="662" y="412"/>
|
||||||
|
<display autosize="true" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
|
sort-features="false" accessors="true" visibility="true">
|
||||||
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
<operations public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
</display>
|
||||||
|
</class>
|
||||||
|
<dependency id="10">
|
||||||
|
<end type="SOURCE" refId="4"/>
|
||||||
|
<end type="TARGET" refId="9"/>
|
||||||
|
</dependency>
|
||||||
|
<dependency id="11">
|
||||||
|
<end type="SOURCE" refId="2"/>
|
||||||
|
<end type="TARGET" refId="9"/>
|
||||||
|
</dependency>
|
||||||
|
<realization id="12">
|
||||||
|
<end type="SOURCE" refId="4"/>
|
||||||
|
<end type="TARGET" refId="3"/>
|
||||||
|
</realization>
|
||||||
|
<association id="13">
|
||||||
|
<end type="SOURCE" refId="5" navigable="false">
|
||||||
|
<attribute id="14" name="author"/>
|
||||||
|
<multiplicity id="15" minimum="0" maximum="1"/>
|
||||||
|
</end>
|
||||||
|
<end type="TARGET" refId="7" navigable="true"/>
|
||||||
|
<display labels="true" multiplicity="true"/>
|
||||||
|
</association>
|
||||||
|
<realization id="16">
|
||||||
|
<end type="SOURCE" refId="2"/>
|
||||||
|
<end type="TARGET" refId="1"/>
|
||||||
|
</realization>
|
||||||
<classifier-display autosize="true" stereotype="true" package="true" initial-value="false" signature="true"
|
<classifier-display autosize="true" stereotype="true" package="true" initial-value="false" signature="true"
|
||||||
sort-features="false" accessors="true" visibility="true">
|
sort-features="false" accessors="true" visibility="true">
|
||||||
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
<attributes public="true" package="true" protected="true" private="true" static="true"/>
|
||||||
|
124
cqrs/etc/cqrs.urm.puml
Normal file
124
cqrs/etc/cqrs.urm.puml
Normal file
@ -0,0 +1,124 @@
|
|||||||
|
@startuml
|
||||||
|
package com.iluwatar.cqrs.util {
|
||||||
|
class HibernateUtil {
|
||||||
|
- LOGGER : Logger {static}
|
||||||
|
- SESSIONFACTORY : SessionFactory {static}
|
||||||
|
+ HibernateUtil()
|
||||||
|
- buildSessionFactory() : SessionFactory {static}
|
||||||
|
+ getSessionFactory() : SessionFactory {static}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
package com.iluwatar.cqrs.app {
|
||||||
|
class App {
|
||||||
|
+ App()
|
||||||
|
+ main(args : String[]) {static}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
package com.iluwatar.cqrs.dto {
|
||||||
|
class Author {
|
||||||
|
- email : String
|
||||||
|
- name : String
|
||||||
|
- username : String
|
||||||
|
+ Author()
|
||||||
|
+ Author(name : String, email : String, username : String)
|
||||||
|
+ equals(obj : Object) : boolean
|
||||||
|
+ getEmail() : String
|
||||||
|
+ getName() : String
|
||||||
|
+ getUsername() : String
|
||||||
|
+ hashCode() : int
|
||||||
|
+ toString() : String
|
||||||
|
}
|
||||||
|
class Book {
|
||||||
|
- price : double
|
||||||
|
- title : String
|
||||||
|
+ Book()
|
||||||
|
+ Book(title : String, price : double)
|
||||||
|
+ equals(obj : Object) : boolean
|
||||||
|
+ getPrice() : double
|
||||||
|
+ getTitle() : String
|
||||||
|
+ hashCode() : int
|
||||||
|
+ toString() : String
|
||||||
|
}
|
||||||
|
}
|
||||||
|
package com.iluwatar.cqrs.commandes {
|
||||||
|
class CommandServiceImpl {
|
||||||
|
- sessionFactory : SessionFactory
|
||||||
|
+ CommandServiceImpl()
|
||||||
|
+ authorCreated(username : String, name : String, email : String)
|
||||||
|
+ authorEmailUpdated(username : String, email : String)
|
||||||
|
+ authorNameUpdated(username : String, name : String)
|
||||||
|
+ authorUsernameUpdated(oldUsername : String, newUsername : String)
|
||||||
|
+ bookAddedToAuthor(title : String, price : double, username : String)
|
||||||
|
+ bookPriceUpdated(title : String, price : double)
|
||||||
|
+ bookTitleUpdated(oldTitle : String, newTitle : String)
|
||||||
|
- getAuthorByUsername(username : String) : Author
|
||||||
|
- getBookByTitle(title : String) : Book
|
||||||
|
}
|
||||||
|
interface ICommandService {
|
||||||
|
+ authorCreated(String, String, String) {abstract}
|
||||||
|
+ authorEmailUpdated(String, String) {abstract}
|
||||||
|
+ authorNameUpdated(String, String) {abstract}
|
||||||
|
+ authorUsernameUpdated(String, String) {abstract}
|
||||||
|
+ bookAddedToAuthor(String, double, String) {abstract}
|
||||||
|
+ bookPriceUpdated(String, double) {abstract}
|
||||||
|
+ bookTitleUpdated(String, String) {abstract}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
package com.iluwatar.cqrs.queries {
|
||||||
|
interface IQueryService {
|
||||||
|
+ getAuthorBooks(String) : List<Book> {abstract}
|
||||||
|
+ getAuthorBooksCount(String) : BigInteger {abstract}
|
||||||
|
+ getAuthorByUsername(String) : Author {abstract}
|
||||||
|
+ getAuthorsCount() : BigInteger {abstract}
|
||||||
|
+ getBook(String) : Book {abstract}
|
||||||
|
}
|
||||||
|
class QueryServiceImpl {
|
||||||
|
- sessionFactory : SessionFactory
|
||||||
|
+ QueryServiceImpl()
|
||||||
|
+ getAuthorBooks(username : String) : List<Book>
|
||||||
|
+ getAuthorBooksCount(username : String) : BigInteger
|
||||||
|
+ getAuthorByUsername(username : String) : Author
|
||||||
|
+ getAuthorsCount() : BigInteger
|
||||||
|
+ getBook(title : String) : Book
|
||||||
|
}
|
||||||
|
}
|
||||||
|
package com.iluwatar.cqrs.domain.model {
|
||||||
|
class Author {
|
||||||
|
- email : String
|
||||||
|
- id : long
|
||||||
|
- name : String
|
||||||
|
- username : String
|
||||||
|
# Author()
|
||||||
|
+ Author(username : String, name : String, email : String)
|
||||||
|
+ getEmail() : String
|
||||||
|
+ getId() : long
|
||||||
|
+ getName() : String
|
||||||
|
+ getUsername() : String
|
||||||
|
+ setEmail(email : String)
|
||||||
|
+ setId(id : long)
|
||||||
|
+ setName(name : String)
|
||||||
|
+ setUsername(username : String)
|
||||||
|
+ toString() : String
|
||||||
|
}
|
||||||
|
class Book {
|
||||||
|
- author : Author
|
||||||
|
- id : long
|
||||||
|
- price : double
|
||||||
|
- title : String
|
||||||
|
# Book()
|
||||||
|
+ Book(title : String, price : double, author : Author)
|
||||||
|
+ getAuthor() : Author
|
||||||
|
+ getId() : long
|
||||||
|
+ getPrice() : double
|
||||||
|
+ getTitle() : String
|
||||||
|
+ setAuthor(author : Author)
|
||||||
|
+ setId(id : long)
|
||||||
|
+ setPrice(price : double)
|
||||||
|
+ setTitle(title : String)
|
||||||
|
+ toString() : String
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Book --> "-author" Author
|
||||||
|
CommandServiceImpl ..|> ICommandService
|
||||||
|
QueryServiceImpl ..|> IQueryService
|
||||||
|
@enduml
|
Loading…
x
Reference in New Issue
Block a user