최대 성능을 위한 Kafka 브로커 구성 가이드

디스크, JVM, 복제, 스레드, 소켓 버퍼, 보존 및 메시지 크기 설정으로 Kafka 브로커 성능을 조정하세요.

최대 성능을 위한 Kafka 브로커 구성 가이드

Kafka는 높은 처리량과 내결함성을 위해 설계되었지만, 브로커 기본값은 여전히 워크로드와 일치해야 합니다. 잘못된 디스크 레이아웃, 힙 크기, 복제 설정 또는 스레드 수는 건강한 클러스터를 지연 문제로 만들 수 있습니다.

이 가이드는 Kafka 브로커 구성의 성능에 초점을 맞춥니다: 디스크 I/O, JVM 크기 조정, 복제 내구성, 요청 스레드, 소켓 버퍼 및 메시지 제한.


1. 고성능 기반 구축

특정 Kafka 브로커 설정을 조정하기 전에 하드웨어 및 운영 체제 계층에서 최적화를 시작해야 합니다. Kafka는 본질적으로 디스크 I/O 및 네트워크에 바인딩됩니다.

디스크 I/O: 중요한 요소

Kafka는 매우 빠른 순차 쓰기에 의존합니다. 그러나 잘못된 디스크 선택이나 부적절한 파일 시스템 구성은 성능을 심각하게 저하시킬 수 있습니다.

설정/선택 권장 사항 근거
스토리지 유형 빠른 SSD (NVMe 권장) 소비자 조회 및 인덱스 작업에 우수한 지연 시간과 랜덤 액세스 성능 제공
디스크 레이아웃 Kafka 로그 전용 디스크 OS 또는 애플리케이션 로그와의 리소스 경합 방지. JBOD(Just a Bunch Of Disks)를 사용하여 여러 마운트 지점의 병렬 I/O 기능을 활용하고, 하드웨어 RAID 대신 Kafka가 복제를 처리하도록 함
파일 시스템 XFS 또는 ext4 XFS는 일반적으로 ext4보다 대용량 및 높은 동시성 작업에 더 나은 성능 제공

OS 튜닝 팁

Linux에서는 커널 및 스토리지 유형에 맞는 I/O 스케줄러를 사용하세요. 이전 커널은 SSD에 대해 deadline 또는 noop을 자주 사용했습니다. 최신 커널은 일반적으로 mq-deadline, none 또는 kyber를 노출합니다. 또한 vm.swappiness를 낮게 유지하여 압력이 가해질 때 브로커 프로세스가 스왑으로 밀려나지 않도록 합니다.

JVM 및 메모리 할당

주요 구성은 Kafka 브로커의 힙 크기입니다. 힙이 너무 크면 긴 GC 일시 중지가 발생하고, 너무 작으면 빈번한 GC 주기가 발생합니다.

모범 사례: Kafka 프로세스에 5GB~8GB의 힙 메모리를 할당합니다(KAFKA_HEAP_OPTS). 나머지 시스템 RAM은 OS가 페이지 캐시로 사용할 수 있도록 남겨두어야 하며, 이는 최근 로그 세그먼트를 빠르게 읽는 데 중요합니다.

# kafka-server-start.sh의 예제 JVM 구성
export KAFKA_HEAP_OPTS="-Xmx6G -Xms6G -XX:+UseG1GC"

2. 핵심 브로커 구성 (server.properties)

이 설정은 데이터가 클러스터 내에서 저장, 복제 및 유지되는 방식을 결정합니다.

2.1 복제 및 내구성

성능은 내구성과 균형을 이루어야 합니다. 복제 요소를 늘리면 내결함성이 향상되지만 모든 쓰기에 대한 네트워크 부하가 증가합니다.

매개변수 설명 권장 값 (예시)
default.replication.factor 새 주제의 기본 복제본 수 3 (표준 프로덕션 값)
min.insync.replicas 프로듀스 요청을 성공으로 간주하는 데 필요한 최소 동기화 복제본 수 2 (RF=3인 경우 높은 내구성 보장)

팁: min.insync.replicasdefault.replication.factor의 N-1로 설정합니다. 프로듀서가 acks=all을 사용하는 경우, 이 설정은 성공을 확인하기 전에 메시지가 필요한 수의 복제본에 기록되도록 보장하여 강력한 내구성을 보장합니다.

2.2 로그 관리 및 크기 조정

Kafka는 주제 데이터를 세그먼트에 저장합니다. 적절한 세그먼트 크기 조정은 순차 I/O를 최적화하고 정리를 단순화합니다.

log.segment.bytes

이 설정은 로그 파일 세그먼트가 새 파일로 롤오버되는 크기를 결정합니다. 더 작은 세그먼트는 더 많은 파일 처리 오버헤드를 유발하는 반면, 너무 큰 세그먼트는 정리 및 장애 복구를 복잡하게 만듭니다.

  • 권장 값: 1073741824 (1 GB)

log.retention.hourslog.retention.bytes

이 설정은 오래된 데이터가 삭제되는 시기를 제어합니다. 성능 이점은 브로커가 관리해야 하는 총 데이터 크기를 최소화하는 데서 오지만, 보존은 비즈니스 요구 사항을 충족해야 합니다.

  • 고려 사항: 주로 시간 기반 보존(예: 7일)을 사용하는 경우 log.retention.hours=168로 설정합니다. 바이트 기반 보존(덜 일반적)을 사용하는 경우 사용 가능한 디스크 공간에 따라 log.retention.bytes를 설정합니다.

3. 네트워크, 스레딩 및 처리량 최적화

Kafka는 내부 스레드 풀을 사용하여 네트워크 요청 및 디스크 I/O를 관리합니다. 이러한 풀을 조정하면 브로커가 동시 클라이언트 연결을 효과적으로 처리할 수 있습니다.

3.1 브로커 스레딩 구성

num.network.threads

이 스레드는 들어오는 클라이언트 요청(네트워크 멀티플렉싱)을 처리합니다. 소켓에서 요청을 읽고 I/O 스레드가 처리할 수 있도록 대기열에 넣습니다. 네트워크 사용량이 높으면 이 값을 늘립니다.

  • 시작점: 3 또는 5
  • 튜닝: 동시 연결 수 및 네트워크 처리량에 따라 조정합니다. 프로세서 코어 수보다 높게 설정하지 마십시오.

num.io.threads

이 스레드는 실제 디스크 작업(로그 세그먼트 읽기 또는 쓰기) 및 백그라운드 작업을 실행합니다. 이 풀은 디스크 I/O를 기다리는 데 가장 많은 시간을 소비합니다.

  • 시작점: 8 또는 12
  • 튜닝: 이 값은 브로커가 호스팅하는 데이터 디렉터리(마운트 지점) 및 파티션 수에 따라 조정되어야 합니다. 더 많은 파티션이 동시 I/O를 요구하면 더 많은 I/O 스레드가 필요합니다.

3.2 소켓 버퍼 설정

적절한 크기의 소켓 버퍼는 특히 높은 지연 시간이나 매우 높은 처리량 요구 사항이 있는 환경에서 네트워크 병목 현상을 방지합니다.

socket.send.buffer.bytessocket.receive.buffer.bytes

이는 TCP 전송/수신 버퍼 크기를 정의합니다. 더 큰 버퍼를 사용하면 브로커가 패킷 손실 없이 더 큰 데이터 버스트를 처리할 수 있으며, 이는 대용량 프로듀서에게 중요합니다.

  • 기본값: 102400 (100 KB)
  • 높은 처리량을 위한 권장 사항: 이 값을 크게 늘려 잠재적으로 524288 (512 KB) 또는 1048576 (1 MB)로 설정합니다.
# 네트워크 및 스레딩 구성
num.network.threads=5
num.io.threads=12

socket.send.buffer.bytes=524288
socket.receive.buffer.bytes=524288
socket.request.max.bytes=104857600

4. 메시지 크기 및 요청 제한

리소스 고갈을 방지하고 네트워크 부하를 관리하기 위해 브로커는 메시지 크기와 요청의 전체 복잡성에 제한을 적용합니다.

4.1 메시지 크기 제한

message.max.bytes

이는 브로커가 수락하는 개별 메시지의 최대 크기(바이트)입니다. 클러스터 전체에서 일관되어야 하며 프로듀서 구성과 일치해야 합니다.

  • 기본값: 1048576 (1 MB)
  • 경고: 이 값을 늘리면 더 큰 페이로드를 허용할 수 있지만, 메모리 소비, GC 압력 및 소비자의 디스크 I/O 지연 시간이 크게 증가합니다. 꼭 필요한 경우에만 늘리십시오.

4.2 백 프레셔 처리

queued.max.requests

이는 네트워크 스레드가 더 많은 요청 읽기를 중지하기 전에 대기열 요청 버퍼에서 대기할 수 있는 최대 요청 수를 정의합니다. I/O 스레드가 네트워크 스레드보다 뒤처질 때 백 프레셔를 적용합니다.

  • 튜닝: 클라이언트가 자주 "브로커 사용 중" 오류를 수신하는 경우 이 값이 너무 낮을 수 있습니다. 메모리 영향을 고려하여 신중하게 늘리십시오.

5. 주요 성능 매개변수 요약

범주 매개변수 성능에 미치는 영향 튜닝 목표
디스크 log.segment.bytes 순차 I/O 효율성, 정리 타이밍 1 GB (I/O 배치 최적화)
내구성 min.insync.replicas 높은 내구성 오버헤드 RF의 N-1로 설정 (복원력 보장)
스레딩 num.io.threads 디스크 읽기/쓰기 동시성 파티션/디스크에 따라 조정 (예: 8-12)
네트워크 num.network.threads 클라이언트 연결 동시성 동시 클라이언트에 따라 조정 (예: 5)
네트워크 socket.send/receive.buffer.bytes 부하 상태의 네트워크 처리량 높은 대역폭/지연 시간에 대해 증가 (예: 512 KB)
제한 message.max.bytes 메시지 페이로드 처리, 메모리 압력 가능한 한 작게 유지 (기본 1MB로 충분한 경우가 많음)

최종 결론

Kafka 브로커 튜닝은 한 번에 하나의 병목 현상을 변경할 때 가장 효과적입니다. 빠른 전용 스토리지, 충분한 페이지 캐시, 합리적인 복제 설정, 그리고 num.io.threads, num.network.threads 및 소켓 버퍼에 대한 측정된 변경부터 시작하십시오. 그런 다음 실제 메시지 크기, 프로듀서 속도, 보존 정책 및 복제 요소로 부하 테스트를 수행하십시오.