이벤트 소싱
이전 포스팅에서 MSA 서비스간 통신하는 여러가지 방법들에 대해 알아보았습니다.
또한, MSA 분산환경에서도 데이터의 일관성을 유지하기위해 SAGA 패턴
을 통해 트랜잭션을 유지하는 방법에 대해서도 확인해 보았는데 아무래도 이벤트 전달 결과만을 DB에 저장하는 특성상 오류에 대한 완벽한 보장을 해 주기 어렵고 이벤트 흐름의 추적도 어려울 수밖에 없습니다.
참고 URL
기존 방식이 다음과 같은 로직을 갖는다고 가정해보겠습니다.
위와같이 작동했을때는 다음과 같은 단점과 한계를 발견 할 수 있습니다.
- Impedance Mismatch : 객체와 테이블의 불일치
- 애그리거트 로그의 부재 : 현재의 상태만 저장되며 수행이력을 저장하려면 별도의 코드개발이 필요
- 심사로그 구현의 어려움 : 보안/통제 및 사용자 액션 자체의 중요성을 위해 로그를 생성할 필요가있는데 코드 구현이 어려울뿐아니라 오류발생 가능성이 높음
- 이벤트 발행로직을 만들며 비즈니스 로직과 결합될 가능성 높음
위와같은 점들을 보완하고자 고안된것이 바로 이벤트 소싱 패턴
입니다.
기존방식의 이벤트를 직접 전달하는것과 다르게, 애그리거트를 DB 이벤트 저장소
에 두고 모든 수행되는 이벤트 액션들을 관리 해 줌으로써 그 자체 테이블이 수행 로그
가 되고 이벤트 발행의 조건
이 되며 정상수행여부 심사
를 할 수 있는 데이터가 되는것입니다.
아래와 같은 예시 테이블처럼 존재 할 수 있습니다.
event_id | event_target | event_type | entity_type | entity_id | event_data | event_status | … |
---|---|---|---|---|---|---|---|
1000 | service A | create | user | 3 | {‘name’:’taes’,’age’:’29’,…} | SUCCESS | … |
1001 | service B | create | order | 1532 | {…} | READY | … |
… | … | … | … | … | … | … | … |
이벤트 소싱 패턴 에서의 이벤트 전달
이벤트 소싱 패턴에서 이벤트 전달은 저장된 이벤트 테이블
을 기반으로 이루어집니다.
이 말 뜻은 이벤트 저장소
의 변경을 확인하여 MSA 서비스로 이벤트를 전달시켜 주어야 하는 것 인데, 이 역할을 이벤트 핸들러
가 수행을 해줍니다.
기본적으로는 DB 폴링
방식을 통해 변경이력이 있는 이벤트들을 이벤트 저장소
에서 불러와 순차적으로 이벤트를 발행해주는 방법과 DB에서 제공해주는 기능인 DB 로그 테일링
을 통해 이벤트 핸들러
를 구현 할 수 있습니다.
이벤트 저장소
에 저장된 모든 이벤트들을 기반으로 로직이 수행되기 때문에 기본적으로 이벤트를 영구저장하는것을 원칙으로 정확성을 담보 할 수 있습니다.
이벤트 소싱 패턴에서는 대략적으로 아래와 같은 구조로 이벤트가 전달 됩니다.
장점
- 이벤트의 확실한 발생 : DB를 통한 이벤트 관리로써, 영속성있는 이벤트 관리를 할 수 있음
- 이벤트 처리 : 이벤트가 정상수행되지 않았다면 재발행을 하거나 보상 이벤트를 수행시키는것이 가능
- 애그리거트 로그 보존 : 이벤트의 전체 이력이 보존되고 임시쿼리를 통해 상태변화들을 확인 가능
- 타임머신 제공 : 수행된 인벤트를 통한 롤백 수행 가능
아쉽지만서도 단점도 존재합니다.
- 이벤트 핸들러의 복잡성 : 메세지기반의 이벤트는 중복이벤트 발행이 일어날수 있기에 멱등성을 고려하여 로직을 구현하거나 중복방지 로직구현이 필요
- 이벤트 확장의 어려움 : 이벤트는 영구저장 되어야 하기 때문에 이벤트의 변경및 확장에 대응하기 어려울 수 있음
- 데이터 삭제의 어려움 : 이벤트는 영구저장 되어야 하기 때문에 이벤트저장소를 거치지 않은 임의의 데이터 삭제가 일어날시 로그 불일치가 일어날 수 있음
오케스트레이션 SAGA + 이벤트 소싱 패턴
이전 포스틍에서 다루었던 Transaction
을 위한 오케스트레이션 SAGA 패턴
과 이벤트 소싱 패턴
을 결합한 구조는 아래와 같습니다.
각 서비스들의 역할을 분리해보자면 다음과 같습니다.
- Service A (오케스트레이션) :
이벤트 저장소
에 이벤트를 저장 - Event Handler :
이벤트 저장소
로부터 변경된 이벤트 발행 - Service B,C (MSA 참여 서비스): 전달받은
이벤트
의 비즈니스 로직 수행
위와같이 목적을 분리하여 이벤트를 좀 더 안전하게 관리 할 수 있을것입니다.