Programming
[CQRS 아는 척하기] CQRS 구현 형태
nineDeveloper
2021. 1. 5. 16:43
728x90
https://www.youtube.com/watch?v=H1IF3BUeFb8&list=PLwouWTPuIjUgr29uSrSkVo8PRmem6HRDE&index=4
CQRS(Command Query Responsibility Segregation)
구현 형태
- 명령과 쿼리 모델이 한 프로세스에 있는지 다른 프로세스에 있는지
- 같은 DB를 사용하는지 다른 DB를 사용하는지
구현: 같은 프로세스, 같은 DB
- 가장 단순
- 명령/쿼리 동일 데이터 보장
구현: 같은 프로세스, 같은 DB, 다른 테이블
명령과 쿼리가 코드 수준에서 분리 되고 데이터 수준에서도 분리되는 방식
단 데이터가 같은 DB에 있는 형태
- 쿼리 전용 테이블 사용
- 예: 최근 조회수 많은 글 목록을 별도 테이블로 따로 저장
- 쿼리 모델은 이 테이블을 이용해서 구현
- 명령이 상태를 변경할때 쿼리 전용 테이블을 함께 변경
구현: 같은 프로세스, 다른 DB
- 예: 상품목록을 레디스와 같은 저장소에 캐싱하고 쿼리 모델은 레디스를 사용하는 방식
- 명령이 데이터를 변경하면 변경내역을 쿼리쪽 DB에 전달
구현: 다른 프로세스, 다른 DB
- 명령이 데이터를 변경하면 변경내역을 쿼리쪽 DB에 전달
- 마이크로서비스 분리 추세에 따라 많이 만날 수 있는 형태
다른 DB로 변경 전파
- 명령이 직접 쿼리 DB를 수정하는 방식
- 카프카와 같은 메세징 수단을 이용해서 전달하는 변형도 있음
- 장점: 구현이 단순함
- 단점: 데이터 유실 가능성이 있음
- 쿼리 DB나 메시징이 일시적으로 장애가 발생하게 되면 쿼리 DB에 반영해야 할 데이터가 유실될 수 있음
- 쿼리 DB나 메시징의 문제 때문에 명령을 수행하는 기능 자체가 에러가 발생할 수 있음
- 변경내역을 기록하고 별도 전파기를 이용해서 변경내역을 전달하는 방식
- 중간에 메시징을 두는 변형이 있음
- 명령은 상태를 변경한 다음 변경내역을 별도 테이블에 기록 함
- 장점: 한 트랜잭션으로 처리 되기 때문에 변경내역이 유실되지 않음
- 단점: 전파기를 별도로 구현해야하는 부담이 있음
- DB가 제공하는 CDC를 사용하는 방식
- 중간에 메시징을 두는 변형이 있음
- DB의 바이너리 로그를 읽어서 변경 데이터를 확인하고 변경된 데이터를 쿼리쪽에 전달하는 방식
- 장점: 명령 쪽 코드에서 변경내역을 따로 저장하지 않아도 되므로 명령코드가 단순해짐
다른 DB 사용시 주의 사항
- 데이터 유실
- 유실 허용 여부에 따라 DB 트랜잭션 범위 중요
- 예
- 주문목록 쿼리 기능의 경우 데이터가 유실되면 곤란함
- 최근 읽기글 쿼리 기능은 일시적으로 데이터 전파가 안되도 치명적이지 않음
- 허용 가능 지연 시간
- 명령의 변경내역을 얼마나 빨리 쿼리쪽에 반영하는지에 따라서 구현의 선택이 달라질 수 있음
- 중복 전달
- 쿼리쪽 DB에 변경된 데이터를 전달하는 과정에서 문제가 발생하게 되면 다시 전달할 수 있는 수단이 필요
- 다시 전달할 수 있는 수단을 만들다 보면 쿼리쪽에 이미 반영된 데이터를 중복으로 전달하는 경우도 발생하게 됨
- 중복으로 데이터를 전달 하더라도 쿼리쪽 데이터가 망가지지 않도록 별도의 처리를 해야 함
참고자료
- CQRS
- CQRS, Task Based Uls, Event Sourcing agh!
정리
시스템이 복잡해질 수록 시스템이 오래 유지보수 될수록 유리해짐
- 명령과 쿼리는 다루는 데이터가 다름
- 명령과 쿼리는 코드 변경 빈도/사용자가 다름
- 기능마다 성능 요구가 다름
728x90