본문 바로가기
Computer Science/개발상식

kafka 아는 척 하기(정리 실패)

by 밍상 2022. 5. 11.

https://www.youtube.com/watch?v=0Ssx7jJJADI&list=WL&index=4&t=1s 

https://www.youtube.com/watch?v=geMtm17ofPY&list=WL&index=27 

https://www.youtube.com/watch?v=xqrIDHbGjOY&list=WL&index=27 

 

카프카란?

분산 이벤트 스트리밍 플랫폼이다.

 

카프카를 사용하려면 크게 4개의 구성 요소.

첫번째는 카프카 클러스터다. 메시지를 저장하는 저장소입니다.

하나의 카프카 클러스터는 여러 개의 브로커로 구성이 된다. 브로커는 각각의 서버 역할을 하는데,

메시지를 나눠서 저장하고, 이중화 처리도 하고, 장애가 나면 대체도 하는 등의 역할을 한다.

 

주키퍼 클러스터가 카프카 클러스터를 관리한다.

 

카프카 클러스터에 메시지를 보내는 것을 프로듀서라고 한다.

프로듀서는 메시지를 카프카에 넣는 역할을 하고, 컨슈머는 메시지를 카프카에서 읽어 오는 역할을 한다.

 

카프카 클러스터는 데이터를 이동하는데 필요한핵심 역할을 맡게 된다.

카프카에서 메시지를 저장하는 단위가 토픽이다. 토픽은 메시즈를 구분하는 용도로 사용한다. 여러 메시지가 있을 때 메시지를 구별하기 위해 사용한다.(뉴스용 토픽, 주문용 토픽)

토픽은 파일시스템의 폴더나 메일함과 유사한 기능을 한다. 한 개의 토픽은 한 개의 이상의 파티션으로 구성된다. 

 

프로듀서와 컨슈머가 토픽을 기준으로 메시지를 주고 받게 된다.

파티션은 추가만 가능한(append-only)파일 입니다.

- 각각의 메시지가 저장되는 위치를 offset이라고 한다.

- 프로듀서가 넣은메시지는 파티션의 맨 뒤에 추가

- 컨슈머는 오프셋 기준으로 메시지를 순서대로 읽음

- 컨슈머의 read 여부와 관계없이 메시지는 삭제되지 않음(설정에 따라 일정 시간이 지난 뒤 삭제)

 

토픽이 여러 파티션으로 구성될 수 있다.

프로듀서는 라운드로빈 또는 키로 파티션 선택

- 같은 키를 갖는 메시지는 같은 파티션에 저장 -> 같은 키는 순서 유지

 

컨슈머는 컨슈머 그룹에 속함.

한 개 파티션은 컨슈머그룹의 한 개 컨슈머만 연결 가능

- 컨슈머그룹에 속한 컨슈머들은 한 카피션을 공유할 수 없음

- 한 컨슈머그룹 기준으러 파티션의 메시지는 순서대로 처리

 

성능

좋음!

- 파티션 파일은 OS 페이지캐시 사용

  - 파티션에 대한 파일 IO를 메모리에서 처리

  - 서버에서 페이지캐시를 카프카만 사용해야 성능에 유리

- Zero Copy

  - 디스크 버퍼에서 네트워크 버퍼로 직접 데이터 복사

- 컨슈머 춘적을 위해 브로커가 하는 일이 비교적 단순

  - 메시지 필터, 메시지 재전송과 같은 일은 브로커가 하지 않음

    - 프로듀서, 컨슈머가 직접 해야 함

  - 브로커는 컨슈머와 파티션 간 매핑 관리

- 묶어서 보내기, 묶어서 받기 (batch)

  - 프로듀서: 일정 크기만큼 메시지를 모아서 전송 가능

  - 컨슈머: 최소 크기만큼 메시지를 모아서 조회 가능

- 낱개 처리보다 처리량 증가

- 처리량 증대(확장)가 쉬움

  - 1개 장비의 용량 한계 -> 브로커 추가, 파티션 추가

  -  컨슈머가 느림 -> 컨슈머 추가 (+파티션 추가)

 

카프카는 장애가 났을때 대처를 위해서 리플리카를 사용합니다.

- 리플리카: 파티션의 복제본

  - 복제수만큼 파티션의 복제본이 각 브로커에 생김

- 리더와 팔로워로 구성

  - 프로듀서와 컨슈머는 리더를 통해서만 메시지 처리

  - 팔로워는 리더로부터 복제

- 장애 대응

  - 리더가 속한 브로커 장애시 다른 팔로워가 리더가 됨

 

프로듀서

- 토픽에 메시지 전송

  - 토픽, 키, 값

batch.size: 배치 크기. 배치가 다 차면 바로 전송

linger.ms: 전송 대기 시간

- 대기 시간이 없으면 배치가 덜 차도 브로커로 바로 전송

- 대기 시간을 주면 그 시간만큼 배치에 메시지 추가가 가능해서 한 번의 전송 요청에 더 많은 데이터 처리 가능

producer.send(new ProducerRecord<>("simple", "value"));

- 전송 실패를 알 수 없음

- 실패에 대한 별도 처리가 필요 없는 메시지 전송에 사용

 

전송 결과를 확인하려면 Future 사용

- future.get에서 블로킹이 발생해서 배치 효과 떨어짐 -> 처리량 저하

- 처리량이 낮아도 되는 경우에만 사용

 

callback 사용시 처리량 저하 없음(exception을 통해 확인)

 

전송 보장과 ask

ack = 0

  - 서버 응답을 기다리지 않음

  - 전송 보장도 zero

ack = 1

  - 파티션의 리더에 저장되면 응답 받음

  - 리더 장애시 메시지 유실 가능

ack = all(or -1)

  - 모든 리플리카에 저장되면 응답 받음

 

프로듀서 에러 유형

- 전송 과정에서 실패

  - 전송 타임 아웃

  - 리더 다운에 의한 새 리더 선출 진행 중

  - 브로커 설정 메시지 크기 한도 초과

- 전송 전에 실패

  - 직렬화 실패, 프로듀서 자체 요청 크기 제한 초과

  - 프로듀서 버퍼가 차서 기다린 시간이 최대 대기 시간 초과

 

실패 대응

- 재시도

- 기록

 

컨슈머

토픽 파티션에서 레코드 조회

토픽의 파티션은 그룹 단위로 할당

파티션 수 < 컨슈머 수 

-> 컨슈머가 놀게 됨

 

컨슈머 설정

- 조회에 영향을 주는 주요 설정

  - fetch.min.bytes: 조회시 브로커가 전송할 최소 데이터 크기

    - 기본값: 1

    - 이 값이 크면 대기 시간은 늘지만 처리량이 증가

  - fetch.max.wait.ms: 데이터가 최소 크기가 될 때까지 기다릴 시간

    - 기본값: 500

    - 브로커가 리턴할 때까지 대기하는 시간으로 poll() 메서드의 대기 시간과 다름

  - max.partition.fetch.bytes: 파티션 당 서버가 리턴할 수 있는 최대 크기

    - 기본값: 1048576 (1MB)

 

자동 커밋 / 수동 커밋

-enable.auto.commit tjfwjd

  - true: 일정 주기로 컨슈머가 읽은 오프셋을 커밋 (기본값)

  - false: 수동으로 커밋 실행

- auto.commit.interval.ms: 자동 커밋 주기

    - 기본값: 5000(5초)

- poll(), close() 메서드 호출시 자동 커밋 실행

'Computer Science > 개발상식' 카테고리의 다른 글

문자 인코딩이란?  (0) 2022.08.11
Apache Kafka vs Amazon SQS  (0) 2022.05.27
CQRS 아는 척 하기  (0) 2022.04.14
NGINX란 무엇인가?  (0) 2022.03.24
UX란 무엇인가?  (0) 2022.01.24