분산 환경에서의 트랜잭션 처리 - Transactional Outbox pattern

분산환경에서의 데이터 전달 방식에 대해

Posted by Yan on September 29, 2024

Transactional Outbox Pattern

분산시스템에서 트랜잭션의 원자성을 보장하기 위해, 분산 트랜잭션(2PC 등)을 활용할 수 있다.
트랜잭션 아웃박스 패턴은 트랜잭션과 이벤트 발행이 원자적으로 처리되어 데이터의 일관성을 보장하기 위해 등장했다.

트랜잭션 내에서 발생한 이벤트를 데이터베이스에 미리 저장해두고, 트랜잭션이 성공적으로 완료된 후에 비동기적으로 메시지로 전송하는 패턴이다.

주요 포인트

  • 데이터베이스 트랜잭션이 커밋되면 메세지를 보내야 한다. 롤백되면, 메세지를 보내선 안된다.
  • 메세지는 서비스에서 보낸 순서대로 메세지 브로커에 보내야 한다.
  • 메세지의 순서는 여러 인스턴스에서 유지되어야 한다.

outbox란, ‘보낼 편지함’이다. 미전송 또는 전송 실패 메세지를 모아두는 것이다.

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

  • 트랜잭션 내 이벤트 저장: 트랜잭션이 성공적으로 완료되기 전에 발생한 이벤트를 임시 테이블이나 별도의 엔티티에 저장합니다.
  • 트랜잭션 커밋: 트랜잭션이 성공적으로 커밋되면 저장된 이벤트를 메시지로 변환합니다.
  • 메시지 전송: 변환된 메시지를 메시지 큐에 전송합니다.

구성

transactionaloutbox

  • Sender : 메시지를 보내는 서비스
  • Database : 비즈니스 엔터티와 메시지 outbox를 저장하는 데이터베이스
  • Message outbox : 관계형 데이터베이스인 경우, 이것은 보낼 메시지를 저장하는 테이블
  • Message relay : 발신함에 저장된 메시지를 메시지 브로커로 전송

Message Relay

Message Relay는 메시지를 한 시스템에서 다른 시스템으로 전달하는 방식이다. 이를 구현하는 방법에는 여러 가지가 있으며, 대표적인 기법으로 Polling PublisherTransaction Log Tailing이 있다.
outbox 테이블은 임시 메시지 큐 역할을 하며 엔티티 업데이트와 함께 트랜잭션으로 묶인다.
Message Relay는 outbox 테이블에 저장하는 데이터를 비동기적으로 읽어서 메시지를 발행하여 메시지 브로커에게 전달하는 역할을 하게 된다.

Message Relay을 구현 방식 2가지

  1. Polling publisher
  2. Transaction log tailing

1. Polling Publisher

Polling Publisher는 주기적으로 데이터베이스(DB)나 메시지 큐를 조회하여 새로운 데이터가 있는지 확인한 후, 이를 전송하는 방식이다.

메세지 릴레이는 조회한 메세지를 하나씩 각자의 목적지 채널로 보내서 메세지 브로커에 발행한다. 그리고 나중에 outbox 테이블에서 메세지를 삭제한다.

특징
  • 일정한 간격으로 폴링(Polling)을 수행하여 데이터를 가져온다.
  • 트랜잭션을 직접 조회하여 메시지를 만들어 내보낸다.
  • 메시지의 전달이 지연될 수 있다(폴링 주기에 따라 다름).
  • 구현이 간단하며 기존 시스템에 쉽게 적용할 수 있다.
동작 방식
  1. 특정 테이블(예: OUTBOX)을 주기적으로 조회한다.
  2. 새로운 메시지가 존재하면 이를 읽어 메시지 브로커(Kafka, RabbitMQ 등)로 전달한다.
  3. 메시지를 보낸 후, 해당 메시지를 처리 완료 상태로 업데이트한다.
  4. 다음 폴링 주기가 오면 다시 조회하고 위 과정을 반복한다.
장점
  • 데이터베이스 변경이 적고, 기존 시스템에 쉽게 적용할 수 있다.
  • 메시지를 보낼 시점을 유연하게 조정할 수 있다.
단점
  • 폴링 주기와 트래픽 간 균형을 맞추기 어렵다.
  • 실시간성이 떨어질 수 있다(폴링 주기에 따라 메시지 전달이 지연됨).
  • 불필요한 쿼리 수행으로 데이터베이스 부하가 발생할 수 있다.

2. Transaction Log Tailing

Transaction Log Tailing은 데이터베이스의 트랜잭션 로그(Transaction Log)를 직접 감시하여 변경 사항을 감지한 후 메시지를 발행하는 방식이다.

특징
  • 데이터베이스 트랜잭션 로그에서 직접 데이터를 읽는다.
  • 메시지를 데이터베이스 변경과 동기화하여 실시간으로 전달할 수 있다.
  • 별도의 애플리케이션 로직을 추가하지 않고도 동작할 수 있다.
동작 방식
  1. 데이터베이스의 트랜잭션 로그를 모니터링한다.
  2. 새로운 변경 사항(INSERT, UPDATE, DELETE)이 발생하면 이를 감지한다.
  3. 감지된 데이터를 기반으로 메시지를 생성하고 메시지 브로커로 전송한다.
  4. 메시지가 정상적으로 전송되었는지 확인하고, 필요하면 재전송을 수행한다.
장점
  • 실시간 메시지 처리가 가능하다.
  • 데이터베이스와 강하게 결합되어 데이터 일관성이 높다.
  • 폴링 방식보다 효율적이며, 불필요한 데이터베이스 부하를 줄일 수 있다.
단점
  • 데이터베이스의 트랜잭션 로그를 읽을 수 있어야 하므로, DBMS에 따라 지원 여부가 다를 수 있다.
  • 로그 분석이 필요하므로, 설정 및 운영이 복잡할 수 있다.
  • 특정 DBMS의 구조에 의존할 수 있다(MySQL의 binlog, PostgreSQL의 WAL 등).

3. Polling Publisher vs Transaction Log Tailing 비교

비교 항목 Polling Publisher Transaction Log Tailing
메시지 감지 방식 주기적으로 DB 조회 트랜잭션 로그 직접 감시
실시간성 지연 발생 가능 (폴링 주기에 따라 다름) 실시간 메시지 감지 가능
DB 부하 주기적인 쿼리 실행으로 부하 발생 가능 로그 기반이므로 DB 부하가 적음
구현 복잡도 상대적으로 단순함 로그 분석 필요, 설정이 복잡할 수 있음
데이터 일관성 애플리케이션이 관리해야 함 DB 트랜잭션과 동기화되어 높은 일관성 유지
적용 용이성 기존 시스템에 쉽게 적용 가능 특정 DBMS의 로그 시스템을 활용해야 함

4. 기타 Message Relay 기법

Change Data Capture (CDC)

  • Transaction Log Tailing을 발전시킨 개념으로, DB의 변경 사항을 감지하고 이를 이벤트로 변환하여 메시지 브로커에 전달하는 방식이다.
  • Kafka의 Debezium 같은 프레임워크를 사용하여 쉽게 구현할 수 있다.
  • 장점: 데이터베이스 트랜잭션과 자연스럽게 연동되며 실시간 메시지 전달이 가능하다.
  • 단점: 운영 및 설정이 복잡하고, DBMS의 CDC 기능을 지원해야 한다.

Event Sourcing

  • 애플리케이션 상태를 변경하는 모든 이벤트를 저장하고, 이를 기반으로 메시지를 생성하는 방식이다.
  • 장점: 이벤트 로그를 기반으로 데이터를 복원할 수 있고, 이벤트 드리븐 아키텍처와 잘 맞는다.
  • 단점: 모든 변경 사항을 이벤트로 저장해야 하므로, 스토리지 비용이 증가할 수 있다.

5. 결론

  • Polling Publisher는 단순한 구현이 가능하지만, 실시간성이 떨어질 수 있다.
  • Transaction Log Tailing은 실시간성을 보장하지만, 설정이 복잡할 수 있다.
  • Change Data Capture (CDC)는 Log Tailing을 보다 고도화한 방식이며, Kafka와 잘 연동된다.
  • Event Sourcing은 메시지 기반 시스템과 강한 결합을 가지며, 이벤트 로그를 관리하는 추가적인 비용이 발생할 수 있다.

reference

트랜잭셔널 아웃박스 패턴의 실제 구현 사례 (29CM)