트랜잭셔널 아웃박스 패턴

카프카 같은 메시지 브로커를 사용할때 로직 수행과 이벤트 발행의 원자성을 보장, 메시발송 순서 보장을 위한 트랜잭셔널 아웃박스 패턴(Transactional Outfox Pattern)을 소개합니다.

트랜잭셔널 아웃박스 패턴이란?

이벤트 드리븐 아키텍처(EDA)는 마이크로서비스 아키텍처(MSA)처럼 여러 서비스가 운영되는 환경에서 서비스 간 통신을 위해 이벤트를 사용하는 아키텍처로, 한 서비스가 이벤트를 발행하고 다른 서비스가 이벤트를 구독하면서 동작합니다. 이러한 방식은 카프카 같은 메시지 브로커를 통해 이벤트를 발행/구독함으로써 서비스간의 직접적인 참조를 제거, 서비스간의 의존성과 결합도를 최소화하도록 지원하는 아키텍처입니다.

클라이언트 요청을 받은 서비스는 로직을 수행하고 이벤트를 발행, 이벤트를 구독하고 있는 서비스들은 발행된 이벤트를 확인하고 서비스가 맡은 역할을 수행합니다. 예로들면 1) 주문 서비스가 주문정보를 데이터베이스에 저장하고 주문이벤트로 발행, 2) 재고 서비스는 주문이벤트를 받아 주문이 발생한 상품의 재고를 처리하면 동작하는것입니다.

위 예에서 주문 서비스가 주문정보를 처리했는데 주문 이벤트 발행에 실패한다면 어떻게 될까요? 주문 서비스와 재고 서비스간의 정합성이 깨지고 재고보다 더 많은 주문을 받거나하는 원하지 않는 상황이 발생할것입니다.

트랜잭셔널 아웃박스 패턴은 이벤트 발행을 테이블(outbox 테이블)에 먼저 기록함으로써 서비스 로직과 이벤트 발행 동작의 트랜잭션을 데이터베이스 레벨에서 처리할 수 있도록 하는 방법입니다. 데이터베이스 레벨의 트랜잭션은 원자성을 보장하므로 로직수행이 실패하면 메시지 발행도 하지 않는것 또한 보장합니다.

트랜잭셔널 아웃박스 패턴 예시

  1. 도메인 로직 처리, outbox 테이블에 발행할 메시지 저장, 이때 두 동작은 하나의 데이터베이스 트랜잭션 단위
  2. 별도 프로세스가 outbox 테이블에 존재하는 메시지를 조회
  3. 2번에서 읽은 메시지를 메시지브로커로 발행
  4. 메시지 발행에 성공하면 outbox 테이블에서 제거

이벤트 발행에 실패하면 outbox 테이블에 이벤트가 여전히 존재하기 때문에 이벤트발행을 계속해서 재시도할수 있기때문에 적어도 한번은 메시지가 발행되는것을 보장할 수 있습니다. 또한 outbox 테이블에 기록된 순서로 이벤트발행을 시도하기 때문에 이벤트 생성 순서대로 이벤트 발행을 보장합니다.

트랜잭셔널 아웃박스 패턴 구현

구현중입니다.

정리

  • 트랙잭셔널 아웃박스 패턴은 outbox에 대한 별도의 테이블을 사용해 서비스의 로직과 이벤트 발행의 원자성을 보장하는 방법

References