2022.10.15(일)
카프카 기초 개념부터 알아두자.
카프카를 구성하는 주요 요소
•
카프카(kafka) or 카프카 클러스터(Kafka cluster) : 데이터를 받아서 전달하는 데이터 버스(data bus) 역할이며, 여러 대의 브로커를 구성한 클러스터를 의미한다. (아파치 프로젝트 애플리케이션 이름)
•
프로듀서(producer) : 카프카에 데이터(메시지)를 만들어서 주는 쪽을 말한다. (클라이언트를 총칭함)
•
컨슈머(consumer) : 데이터(메시지)를 빼내서 소비하는 쪽을 말한다. (클라이언트를 총칭함)
•
토픽(topic) : 메시지 피드들을 토픽으로 구분함, 각 토픽의 이름은 카프카 내에 고유하다.
•
주키퍼(ZooKeeper) : 카프카의 정상 동작을 보장하기 위해 메타데이터를 관리하는 코디네이터이며, 브로커의 정상상태 점검(health check)를 담당한다.
•
브로커(broker) : 카프카 애플리케이션이 설치된 서버 또는 노드이다.
•
파티션(partition) : 병렬 처리 및 고성능을 얻기 위해 하나의 토픽을 여러 개로 나눈 것을 말한다.
•
세그먼트(segment) : 프로듀서가 전송한 실제 메시지가 브로커의 로컬 디스크에 저장되는 파일을 말한다.
•
메시지(message) or 레코드(record) : 프로듀서가 브로커로 전송하거나 컨슈머가 읽어가는 데이터 조각을 말한다.
리플리케이션
예시) --partition 1, --replication-factor 3
위 옵션으로 peter-overview01 토픽 생성
의미)
--replication-factor 3 : 카프카 내 원본을 포함한 3개의 리플리케이션을 유지하겠다.
JavaScript
•
각 메시지들을 여러 개로 복제해서 카프카 클러스터 내 브로커들에 분산시키는 동작을 말한다.
•
리플리케이션 동작으로 하나의 브로커가 종료되어도 카프카는 안정성을 유지할 수 있다.
•
주의할 점
◦
리플리케이션 팩터 수가 커지면 안정성은 높아짐, But 브로커 리소스를 많이 사용하게 됨
◦
복제에 대한 오버헤드를 줄여 최대한 브로커를 효율적으로 사용해야 함
•
토픽 생성 시 리플리케이션 팩터 수를 기준을 세워 효율적으로 카프카 운영하기
4 또는 5 이상으로 설정 가능하지만, 운영 경험 상 3일 경우 충분히
안정성 보장 및 적절한 디스크 공간을 사용할 수 있다.
◦
테스트 및 개발환경 : 1로 설정
◦
운영 환경(로그성 메시지로서 약간의 유실 허용) : 2로 설정
◦
운영 환경(유실 허용하지 않음) : 3으로 설정
파티션
•
하나의 토픽이 한 번에 처리할 수 있는 한계를 높이기 위해, 하나의 토픽을 여러 개로 나눠 병렬 처리하는 것을 파티션이라고 한다. 이를 통해 병렬 처리뿐만 아니라, 분산 처리도 가능해진다.
•
주의할 점
컨슈머의 LAG
프로듀서가 보낸 메시지 수(카프카에 남아 있는 메시지 수) - 컨슈머가 가져간 메시지 수
LAG 지표를 통해 컨슈머에 지연을 확인할 수 있다.
◦
파티션 번호는 0부터 시작한다.
◦
❗️한 번 늘린 파티션 수는 절대로 줄일 수 없다.
◦
위와 같은 이유로 초기에 작게 유지하면서 메시지 처리량 & 컨슈머의 LAG 등을 모니터링하여 조금씩 늘려야 한다.
◦
적절한 파티션 수를 산정하기 위해 계산해주는 사이트(https://eventsizer.io/)도 존재한다. 그러나 무조건 가이드를 따라야 하는 것은 아니므로 이를 꼭 참고하자.
세그먼트
•
프로듀서에 의해 브로커로 전송된 메시지는 토픽의 파티션에 저장되고,
각 메시지들은 세그먼트라는 로그 파일의 형태로 브로커의 로컬 디스크에 저장된다.
프로듀서 → 브로커 → 파티션 → 브로커의 로컬 디스크(세그먼트 형태)
예시
1.
프로듀서는 카프카의 peter-overview01 토픽으로 메시지 전송
2.
peter-overview01 토픽은 파티션이 하나뿐이므로,
프로듀서로부터 받은 메시지를 파티션0의 세그먼트 로그 파일에 저장
3.
브로커의 세그먼트 로그파일에 저장된 메시지는 컨슈머가 읽어감
카프카는 왜 안정적이고, 높은 처리량을 갖게 되었을까?
위 질문에 답할 수 있는 핵심 개념에 대해서 알아보자.
분산 시스템
•
분산 시스템은 성능이 높다는 장점도 있지만, 하나의 서버에서 장애 발생 시 다른 서버가 처리 가능하기 때문에 장애 대응에 탁월하다. 그리고 부하가 높은 경우에 시스템 확장이 용이하다는 점이 있다.
•
카프카도 분산 시스템이므로 한계치에 도달했다면 브로커를 추가하는 방식으로 확장이 가능하다.
페이지 캐시
•
높은 처리량을 위해 추가된 기능이다. 카프카는 OS의 페이지 캐시를 활용하는 방식으로 설계되어 있다.
(운영체제(OS)는 성능을 높이기 위해 꾸준히 발전되고 있는데 특히 페이지 캐시 활용이 대표적이다)
•
해당 기능으로 디스크 I/O에 대한 접근이 줄어든다. (카프카
페이지 캐시
디스크)
배치 전송 처리
•
수 많은 통신들을 묶어서 처리한다면 네트워크 오버헤드를 줄일 수 있고, 장기적으로 더욱 빠르고 효율적으로 처리 가능하다. 따라서 배치 전송이 단건 전송보다 훨씬 효율적이다.
•
카프카는 위와 같은 장점을 지닌 배치 전송을 권장한다.
압축 전송
•
카프커에서 성능이 높은 압축 전송을 사용하는 것을 권장한다. (지원하는 압축 방식은 gzip, snappy, lz4, zstd 등이 있다)
◦
높은 압축률이 필요한 경우 : gzip, zstd 권장
◦
빠른 응답 속도가 필요한 경우 : lz4, snappy 권장
◦
그러나 위와 같이 절대적인 기준은 없으나 직접 테스트 해보고 결정하는 것이 좋다.
•
압축만으로 네트워크 대역폭이나 회선 비용 등을 줄일 수 있으므로, 배치 전송과 결합해 사용한다면 높은 효과를 얻을 수 있다.
토픽, 파티션, 오프셋
•
토픽 : 카프카는 토픽에 데이터를 저장한다. (메일 전송 시스템에서 이메일 주소 정도로 이해)
•
파티션 : 토픽은 병렬 처리를 위해 여러 개의 파티션으로 나뉜다.
즉, 하나의 토픽도 높은 처리량을 수행할 수 있다.
•
오프셋(offset) : 파티션의 메시지가 저장되는 위치이며, 순차적으로 증가하는 숫자(64비트 정수) 형태이다. 이를 통해 메시지 순서를 보장하고 컨슈머에서 마지막까지 읽은 위치를 알 수 있다.
고가용성 보장
•
카프카는 분산 시스템이라 하나가 다운되어도, 다른 곳에서 역할을 대신해 안정적인 서비스가 가능하다.
•
원본과 리플리케이션을 구분하기 위해 카프카에서는 리더와 팔로워라고 부른다.
참고로 리플리케이션은 토픽 자체를 복제하는 것이 아니라 토픽의 파티션을 복제하는 것이다.
◦
리더(reader) : 프로듀서, 컨슈머로부터 오는 모든 읽기와 쓰기 요청을 처리한다.
◦
팔로워(follower) : 오직 리더로부터 리플리케이션하게 된다.
주키퍼의 의존성
•
주키퍼는 지노드를 이용해 브로커의 노드 관리, 토픽 관리, 컨트롤러 관리 등 매우 중요한 역할을 하고 있다.
◦
지노드(znode) : 카프카의 메타 정보가 주키퍼에 기록된다.
•
2021년 말 또는 22년 초 무렵 주키퍼가 삭제된 버전이 릴리즈
◦
카프카가 성장하면서 주키퍼 성능의 한계가 드러났다.
프로듀서는 어떻게 동작할까?
프로듀서 디자인 및 전체 흐름
1.
ProducerRecord : 카프카로 전송하기 위한 실제 데이터이며 아래와 같이 구성된다.
•
레코드는 토픽, 파티션, 키, 벨류로 구성
•
레코드 전송할 때, 카프카의 특정 토픽으로 메시지 전송하는데 토픽, 벨류(메시지 내용)은 필수 & 특정 파티션을 지정하는 파티션과 레코드들을 정렬하기 위한 키는 선택사항이다.
2.
프로듀서의 send() 메소드를 통해 시리얼라이저와 파티셔너를 거치게 된다.
•
파티션을 지정한 경우 : 파티셔너는 아무 동작하지 않고 지정된 파티션으로 레코드를 전달한다.
•
파티션을 지정하지 않은 경우 : 키를 가지고 파티션을 선택해 레코드를 전달한다. 그리고 기본적으로 라운드 로빈 방식으로 동작한다.
•
send() 메소드 호출 이후 : 레코드들을 파티션별로 잠시 모아둔다. 프로듀서가 카프카 전송 전, 배치 전송을 하기 위함이다. (전송 실패 시 재시도 동작을 하게 되고, 지정된 횟수만큼 재시도하게 되면 최종 실패하게 됨, 성공 시 메타 데이터 반환 )