CQRS (Command Query Responsibility Segregation)

image.png
bertrand meyer의 책 객체 지향 소프트웨어에서 시작된 개념. 상태를 변경하는 명령과 단순 질의를 분리하여, 응집력있는 프로그램을 만드는 것.
구현 방식 : command가 발생하면 변경된 결과가 query에 전달되어 update된 상태를 반영한다. db는 두 model간 communication을 담당.

장점

  1. 복잡한 도메인에서는 query, command를 나누는 것이 쉬우나, 극히 일부의 예이다. 대개는 두 모델을 공유하는 것이 훨씬 나으며, 이런 경우 CQRS를 사용하면 복잡도만 증가한다.
  2. ::고성능 어플리케이션::을 위해 사용될 수 있다. query, command에 각각 다른 전략을 사용할 수 있다. (서버를 늘리거나, 캐시를 적용하거나)

단점

복잡도가 늘어날 수 있다. 대부분은 CRUD mental model에 맞으며, 큰 이점이 없는 이상 함부러 사용해서는 안되며 전체 시스템에 적용해서는 더욱 안된다.
CQRS에는 적합하지 않지만, query나 성능 문제를 해결해야 하는 경우, ReportingDatabase를 사용하면 된다.
command model는 update에 대한 이벤트를 생성하고, query model은 event poster를 활용하여 같이 사용할 수 있다.

ReportingDatabase

image.png

사용자의 operation 요구사항과 report 되는 요구사항은 다를 수 있다. 이런 경우 특정 operation만을 copy해온 report db를 별도로 유지한다.

장점

  1. report 요구사항에 맞게 스키마를 원하는 대로 변경할 수 있다.
  2. 읽기 전용이므로 normalize할 필요없다. 여기저기 다 데이터 중복해서 보기 편한대로 저장한다.
  3. 트래픽 및 운영이 분리된다.

단점

  1. 데이터 동기화. 최신 데이터로 유지하는 비용.

EventPoster

어플리케이션은 주로 어떤 상태에 대한 표시를 사용자에게 보여주는 것이며, 변경 사항은 저장/큐에 쌓을 수 있는 event 목록으로 만들어진다. DB는 현재의 상태를 저장할 필요가 없으며, 초기값과 이후의 event를 저장하기만 하면 된다. 특정 상태를 복원하고 싶으면 그 상태까지 replay만 하면 된다.

장점

  1. disk가 필요없으며, 매우 빠르다.
  2. 메모리-DB간 매핑 복잡성이 줄어든다.

일반적으로 모든 event를 유지하는 것은 어려우므로 주기적으로 최신 스냅샷을 생성한다.

Event Sourcing

어플리케이션의 모든 변경 사항을 이벤트로 저장한다. 저장된 이벤트로 특정 시점의 상태를 재구성할 수 있다.

참고

Martin Fowler: eaaDev