1.시스템&인프라/Apache Kafka

5. Kafka 리더 장애 발생 시 Failover를 위한 Producer와 Consumer 설정

쿼드큐브 2025. 3. 28. 20:42
728x90
반응형

Kafka 클러스터에서 리더 브로커가 장애를 일으키면, Kafka는 자동으로 새로운 리더를 선출합니다. 하지만 Producer와 Consumer가 새로운 리더로 자동 연결되도록 하려면, 클라이언트 설정이 올바르게 구성되어 있어야 합니다. 이 글에서는 Kafka 클라이언트(Producer/Consumer)에서 자동 리더 전환(Failover)을 제대로 지원하는 조건과 설정 방법을 상세히 설명합니다.

 

Kafka 리더 장애 발생 시 Failover를 위한 Producer와 Consumer 설정

 

목차

1. Kafka의 리더 장애 처리 과정

2. Producer 설정: 자동 리더 전환(Failover)을 위한 조건

3. Consumer 설정: 자동 리더 감지 및 재 연결

4. bootstrap.servers 설정의 중요성

5. Kafka 안정성을 높이는 설정

관련 글 링크

 

 

1. Kafka의 리더 장애 처리 과정

Kafka는 각 파티션에 대해 리더 브로커를 운영합니다. 이 리더는 장애 발생 시 다음과 같은 과정을 통해 자동 전환됩니다:

  1. Kafka 컨트롤러 브로커가 리더 브로커의 다운을 감지
  2. ISR(In-Sync Replicas) 내 팔로워 중 하나가 자동으로 새로운 리더로 승격
  3. Kafka 클라이언트는 메타데이터를 갱신하여 새로운 리더로 전환
  4. Producer/Consumer는 리더 전환을 인식하고 자동으로 재연결

단, 이 모든 과정은 클라이언트가 적절한 설정을 갖췄을 때만 원활히 작동합니다.

 

 

2. Producer 설정: 자동 리더 전환(Failover)을 위한 조건

Kafka 3.9 기준으로, 다음과 같은 설정이 리더 전환 시 Producer가 안정적으로 재시도하고 복구하도록 도와줍니다.

  • 설정 옵션:
bootstrap.servers=broker1:9092,broker2:9092,broker3:9092
acks=all
retries=5
retry.backoff.ms=100
metadata.max.age.ms=120000
delivery.timeout.ms=120000
request.timeout.ms=30000
설정 키 설명
bootstrap.servers 클러스터 초기 접속용 브로커 주소 (최소 2~3개)
acks=all 리더와 복제본 모두가 메시지를 저장해야 전송 성공 처리
retries=5 메시지 전송 실패 시 재시도 횟수
retry.backoff.ms=100 재시도 전 대기 시간
metadata.max.age.ms=120000 메타데이터 강제 갱신 주기 (기본 5분 → 2분 권장)
delivery.timeout.ms=120000 전체 메시지 전송 제한 시간 (Kafka 2.1 이상 필수)
request.timeout.ms=30000 브로커 응답 대기 시간 (너무 짧으면 불안정)
 
  • Java 코드 예시:
Properties props = new Properties();
props.put("bootstrap.servers", "broker1:9092,broker2:9092,broker3:9092");
props.put("acks", "all");
props.put("retries", 5);
props.put("retry.backoff.ms", 100);
props.put("metadata.max.age.ms", 120000);
props.put("delivery.timeout.ms", 120000);
props.put("request.timeout.ms", 30000);
props.put("key.serializer", "org.apache.kafka.common.serialization.StringSerializer");
props.put("value.serializer", "org.apache.kafka.common.serialization.StringSerializer");

KafkaProducer<String, String> producer = new KafkaProducer<>(props);
 

 

3. Consumer 설정: 자동 리더 감지 및 재 연결

"자동 리더 감지 및 재연결" 자체는 Consumer Group 없이도 가능합니다.

하지만 파티션 재할당(리밸런싱) 및 장애 복구 후 자동 복원 기능은 Consumer Group이 있어야 제대로 작동합니다.

 

Kafka는 Consumer Group을 통해 파티션을 자동으로 배분(assign)합니다.

장애로 리더가 변경되거나 Consumer가 죽으면, 리밸런싱이 자동 수행되어 다른 Consumer가 파티션을 이어받습니다.

Consumer Group이 있어야 다음과 같은 기능이 자동으로 작동합니다:

  • Consumer 장애 시 재할당
  • 새 Consumer 참여 시 동적 분배
  • 리더 변경 시 자동 poll 재연결
  • 오프셋 관리 (commit)

Consumer도 자동 리더 전환을 감지하고 새로운 리더에게 파티션을 재할당받기 위해 다음과 같은 설정이 필요합니다.

  • 설정 옵션:
bootstrap.servers=broker1:9092,broker2:9092
group.id=my-consumer-group
enable.auto.commit=true
auto.offset.reset=latest
metadata.max.age.ms=120000
session.timeout.ms=10000
heartbeat.interval.ms=3000
max.poll.interval.ms=300000
설정 키 설명
group.id Consumer Group 지정 (필수)
enable.auto.commit 오프셋 자동 커밋 허용
auto.offset.reset 오프셋이 없을 때 시작 위치 지정 (latest 또는 earliest)
metadata.max.age.ms 메타데이터 갱신 주기
session.timeout.ms 브로커와 연결이 끊겼다고 판단하는 시간
heartbeat.interval.ms 하트비트 전송 간격 (세션 유지용)
max.poll.interval.ms poll() 호출 간 최대 대기 시간 (백그라운드 작업 시 중요)
  • Java 코드 예시:
Properties props = new Properties();
props.put("bootstrap.servers", "broker1:9092,broker2:9092");
props.put("group.id", "my-consumer-group");
props.put("enable.auto.commit", "true");
props.put("auto.offset.reset", "latest");
props.put("metadata.max.age.ms", "120000");
props.put("session.timeout.ms", "10000");
props.put("heartbeat.interval.ms", "3000");
props.put("max.poll.interval.ms", "300000");
props.put("key.deserializer", "org.apache.kafka.common.serialization.StringDeserializer");
props.put("value.deserializer", "org.apache.kafka.common.serialization.StringDeserializer");

KafkaConsumer<String, String> consumer = new KafkaConsumer<>(props);
consumer.subscribe(Collections.singletonList("topic-1"));

while (true) {
    ConsumerRecords<String, String> records = consumer.poll(Duration.ofMillis(1000));
    for (ConsumerRecord<String, String> record : records) {
        System.out.printf("Consumed: key=%s, value=%s, offset=%d%n",
                          record.key(), record.value(), record.offset());
    }
}

 

 

4. bootstrap.servers 설정의 중요성

bootstrap.servers=broker1:9092,broker2:9092,broker3:9092
  • 클러스터 접속을 위한 시작점(부트스트랩 주소) 역할
  • Kafka는 이 주소로 접속한 후 전체 브로커 정보를 가져와 저장
  • 반드시 2개 이상 브로커를 설정해야 한 브로커가 다운돼도 접속 가능

 

5. Kafka 안정성을 높이는 설정

Kafka 2.1 이후부터는 retries, delivery.timeout.ms, request.timeout.ms의 상호작용이 중요합니다.
delivery.timeout.ms 안에서만 재시도가 발생하므로, 전체 전송 시간을 기준으로 전략을 잡아야 합니다.

설정 키  역할
retries 전송 실패 시, 최대 몇 번까지 재시도할지 설정
request.timeout.ms 한 번의 요청에서 브로커 응답을 기다리는 최대 시간
delivery.timeout.ms 전체 전송 시도에 허용되는 총 시간 (이 시간이 지나면 무조건 실패)

1. Kafka Producer가 메시지를 전송할 때는 다음과 같은 과정이 있습니다:

  1. 브로커에 메시지를 보냄
  2. 응답을 기다림 → 응답이 없으면 실패
  3. 실패한 경우 retries 횟수만큼 다시 시도
  4. 이 모든 재시도 동작은 delivery.timeout.ms 내에서만 유효함

2. 상호작용 구조:

  • Kafka는 메시지를 전송할 때, retries 횟수만큼 재시도를 허용하지만
  • delivery.timeout.ms 시간 안에서만 retry가 일어납니다.
  • 즉, retries가 아무리 커도, delivery.timeout.ms 안에 전송이 완료되지 않으면 실패로 처리됩니다.

3. 예시:

retries=5
request.timeout.ms=10000
delivery.timeout.ms=30000

이 경우:
 - 한 번 요청하고 응답을 최대 10초 기다립니다
 - 실패하면 최대 5번까지 재시도할 수 있지만
 - 전체 전송 제한 시간은 30초이므로

실제로는 10초 x 3회 = 30초까지만 가능하고, 3번만 재시도하고 실패합니다.
즉, retries=5이지만, 실제 재시도는 최대 3번만 발생합니다.

 

4. 조합 예:

목적 조합 예
재시도를 많이 하고 싶다 retries=5 이상,
request.timeout.ms를 짧게 (ex. 5000),
delivery.timeout.ms를 길게 (ex. 60000)
빠르게 실패하고 대기하지 않기 delivery.timeout.ms를 작게 설정 (ex. 15000)
장애 상황에서 복구 기다리기 delivery.timeout.ms를 여유롭게 설정 (ex. 120000),
retry.backoff.ms로 간격 조절

Kafka는 리더 장애 상황에서도 서비스 중단 없이 자동으로 리더를 전환할 수 있는 강력한 구조를 가지고 있습니다.
하지만 이 기능을 클라이언트 측에서 제대로 활용하려면, 적절한 설정과 안정적인 연결 전략이 필수입니다.

Producer와 Consumer 설정을 잘 구성하면 장애 발생 시에도 시스템이 안정적으로 작동하고,복잡한 장애 대응 로직 없이도 자동 복구 환경을 구축할 수 있습니다.

 

 

관련 글 링크

 

Apache Kafka Simple Producer Example

Discover how to create a simple Kafka producer and send messages to topics in this detailed example.

www.tutorialspoint.com

 

Chapter 5. Kafka producer configuration tuning | Red Hat Product Documentation

FormatMulti-pageSingle-pageView full doc as PDF

docs.redhat.com

 

728x90
반응형