MirrorMaker 2 — 클러스터 경계를 넘는 복제, 그리고 offset 동기화의 함정
서울 리전의 Kafka 클러스터가 장애 났다. DR 사이트(도쿄)에 복제해둔 토픽 데이터는 살아 있다. 하지만 장애 복구팀이 가장 먼저 듣는 질문은 이것이다: "consumer offset은요?" 데이터는 복제됐지만, consumer 그룹이 어디까지 읽었는지는 복제되지 않았다. 수천 개의 partition에 대해 consumer가 마지막으로 읽은 위치를 모른다 — 백로그를 처음부터 다시 처리하거나, 하루 전 체크포인트로 수동 복구해야 한다.
이것이 MirrorMaker 1 시절의 현실이었다. MirrorMaker 2(MM2)는 이 문제를 근본적으로 다시 설계했다 — 데이터만 복제하는 것이 아니라, consumer offset, 토픽 설정, ACL까지 함께 옮기는 Connect 기반 복제 프레임워크로. 이 글은 MM2가 무엇인지부터 시작해, 구성 방법, 멀티 리전 offset 동기화의 작동 원리와 함정, 그리고 프로덕션 운영에서 반드시 알아야 할 것들을 다룬다.
이 글은 Kafka의 클러스터 내 복제(intra-cluster replication, ISR/HW)가 아닌 클러스터 간 복제(inter-cluster replication)를 다룬다. 클러스터 내 복제는
06-replication.md참조.
MM2란 — Connect 위에 구축된 크로스 클러스터 복제 프레임워크
MM2는 서로 다른 Kafka 클러스터 간에 토픽 데이터, 토픽 설정, consumer 그룹 offset, ACL을 복제하는 도구다. (geo-replication.md) 핵심은 Kafka Connect 프레임워크 위에 구축됐다는 점 — Connect의 task 분산, 장애 복구, 내부 topic 기반 상태 저장을 그대로 상속받는다. (10-connect.md 참조)
MM2는 세 가지 커넥터로 구성된다:
flowchart TD
subgraph MM2["MirrorMaker 2 (Connect 기반)"]
SC["MirrorSourceConnector<br/>토픽 데이터 + 설정 + ACL 복제"]
CC["MirrorCheckpointConnector<br/>consumer offset 체크포인트 + 변환"]
HC["MirrorHeartbeatConnector<br/>연결 상태 모니터링"]
end
SRC["source cluster<br/>(예: us-west)"] --> SC
SRC --> CC
SRC --> HC
SC --> TGT["target cluster<br/>(예: us-east)"]
CC --> TGT
HC --> TGT
| 커넥터 | 역할 | 기본 활성화 |
|---|---|---|
| MirrorSourceConnector | source topic의 record를 target으로 복제. 토픽 설정·ACL도 동기화 | 예 |
| MirrorCheckpointConnector | source consumer 그룹의 offset을 target 기준으로 변환해 checkpoint topic에 기록. sync.group.offsets.enabled=true 시 target의 __consumer_offsets에 직접 기록 |
예 (단, offset 동기화는 기본 비활성화) |
| MirrorHeartbeatConnector | target cluster에 heartbeat을 주기적으로 발행하여 연결 상태를 추적 가능하게 함 | 예 |
MirrorMaker 1은 단순한 "source consumer + target producer" 조합이었다. offset 동기화, ACL 복제, 자동 토픽 감지, 루프 방지 기능이 없었다. MM2는 KIP-382(Kafka 2.4)에서 도입됐다. (KIP-382)
복제 흐름(replication flow) — 방향성이 있는 데이터 이동
MM2의 핵심 단위는 replication flow다. {source}->{target} 형식으로 정의하며, 방향성이 있다 — 양방향 복제가 필요하면 두 flow를 각각 활성화해야 한다. (geo-replication.md)
flowchart LR
subgraph patterns["복제 토폴로지 패턴"]
A1["Active/Passive<br/>A->B"]
A2["Active/Active<br/>A->B, B->A"]
A3["Aggregation<br/>A->K, B->K, C->K"]
A4["Fan-out<br/>K->A, K->B, K->C"]
end
가장 많이 쓰이는 두 패턴:
- Active/Passive (A->B): primary에서 secondary로 단방향 복제. DR(disaster recovery) 용도. 장애 시 secondary로 전환(failover).
- Active/Active (A->B, B->A): 양방향 복제. 두 리전 모두 생산·소비. 지연 허용 오차가 큰 워크로드.
Active/Active에서 복제 "루프"(A→B로 복제된 데이터가 다시 B→A로 복제되는 현상)는 같은 MM2 설정 파일에 두 flow를 정의하면 자동으로 방지된다. MM2가 복제된 토픽(이름에 source alias가 붙은)을 식별해 되복제하지 않기 때문. (geo-replication.md)
복제된 토픽의 이름 규칙 — DefaultReplicationPolicy
MM2는 source topic을 target으로 복제할 때 이름 앞에 source cluster alias를 붙인다. 기본 DefaultReplicationPolicy에 따른 규칙: {source_alias}.{topic_name} (DefaultReplicationPolicy.java)
us-west (source) us-east (target)
================ =================
foo-topic --> us-west.foo-topic
bar-topic --> us-west.bar-topic
이 이름 변형이 왜 필요한가 — 같은 토픽 이름을 가진 데이터가 출처가 섞이는 것을 막기 위해. Active/Active에서 foo 토픽이 양쪽에 있다면, us-west의 foo는 us-east에 us-west.foo로, us-east의 foo는 us-west에 us-east.foo로 복제된다. 루프 없이 출처가 추적 가능하다.
구분자(separator)는 기본 .이지만 변경 가능:
# 커스텀 구분자
replication.policy.separator = _
# 결과: us-west_foo-topic
완전히 다른 이름 규칙이 필요하면 replication.policy.class로 커스텀 ReplicationPolicy 구현체를 지정할 수 있다. (IdentityReplicationPolicy를 쓰면 이름 변형을 하지 않지만, Active/Active에서는 루프 위험이 있으므로 주의.)
이름 규칙이 consumer에게 영향을 준다 — target에서 소비하려면 원래
foo-topic이 아니라us-west.foo-topic을 구독해야 한다. 이는 장애 전환(failover) 시 consumer 설정 변경이 필요하다는 의미이기도 하다.
MM2 구성 — 설정 파일 한 개로 모든 것을
MM2는 단일 설정 파일(connect-mirror-maker.properties)로 모든 복제를 정의한다. 이 파일에 cluster 정의, 복제 flow, Connect/producer/consumer 설정이 모두 들어간다.
전체 구성 예시 — Active/Passive
# Kafka 4.3, KRaft
# cluster alias 정의
clusters = primary, secondary
# 각 cluster 연결 정보
primary.bootstrap.servers = broker1-primary:9092,broker2-primary:9092
secondary.bootstrap.servers = broker1-secondary:9092,broker2-secondary:9092
# 복제 flow 활성화 (primary -> secondary 단방향)
primary->secondary.enabled = true
secondary->primary.enabled = false
# 복제할 토픽 (정규식)
primary->secondary.topics = .*
# 내부 topic 복제 팩터 (프로덕션: 3 이상 권장)
replication.factor = 3
checkpoints.topic.replication.factor = 3
heartbeats.topic.replication.factor = 3
offset-syncs.topic.replication.factor = 3
# Connect 내부 topic 복제 팩터
offset.storage.replication.factor = 3
status.storage.replication.factor = 3
config.storage.replication.factor = 3
# consumer 그룹 offset 동기화 활성화 (DR 핵심 설정)
sync.group.offsets.enabled = true
sync.group.offsets.interval.seconds = 60
emit.checkpoints.enabled = true
emit.checkpoints.interval.seconds = 60
# 복제에서 제외할 토픽 (내부 topic 제외)
topics.exclude = .*[\-\.]internal, .*\.replica, __.*
(connect-mirror-maker.properties 예시) (MirrorConnectorConfig.java)
설정 문법의 계층 구조
MM2 설정은 전역 기본값 → flow별 오버라이드 계층을 가진다:
# 전역 기본값 (모든 flow에 적용)
topics = .*
groups = .*
# flow별 오버라이드
primary->secondary.topics = foo.*, bar.*
primary->secondary.groups = important-.*
또한 Connect, producer, consumer 설정을 cluster별로 커스터마이징할 수 있다:
# source cluster consumer 설정
primary.consumer.isolation.level = read_committed
# target cluster producer 설정
secondary.producer.compression.type = gzip
secondary.producer.buffer.memory = 32768
실행
# Kafka 4.3, KRaft 단일 노드 환경
# 전체 flow 실행
bin/connect-mirror-maker.sh config/connect-mirror-maker.properties
# 특정 target만 (consume from remote, produce to local)
bin/connect-mirror-maker.sh config/connect-mirror-maker.properties --clusters secondary
--clusters옵션은 특정 target cluster에 가까운 위치에서만 실행할 때 사용. producer가 원격 cluster로 보낼 때 발생하는 지연(producer lag)을 줄이는 공식 권장 사항이다. (geo-replication.md)
멀티 리전 offset 동기화 — 이 글의 핵심
DR 시나리오에서 가장 중요한 질문으로 돌아가자: 장애 전환 후 consumer가 어디서부터 읽어야 하는가? MM2는 이 문제를 offset 변환(translation)으로 푼다.
offset이 왜 다른가 — 복제 과정에서 발생하는 offset 불일치
source에서 offset 100인 record가 target으로 복제되면, target에서의 offset이 100이라는 보장이 없다. 이유:
- source와 target의 파티션 수가 다를 수 있다 (MM2는 partition 수를 동기화하려 하지만, 기존 토픽이 이미 있는 경우는 다를 수 있음).
- source에서 retention으로 일부 record가 삭제됐을 수 있다.
- 복제 중 일부 record가 누락됐거나 재시도로 인해 순서가 다를 수 있다.
따라서 source offset 100이 target에서는 offset 97일 수도 있고 103일 수도 있다. 이 매핑을 저장하고 변환하는 것이 offset 동기화의 본질이다.
MM2의 offset 동기화 메커니즘
MM2는 offset 동기화를 두 단계로 수행한다:
flowchart TD
subgraph 1단계["1단계: offset 매핑 기록"]
S1["MirrorSourceConnector<br/>record 복제"] --> OST["offset-syncs topic<br/>source offset → target offset 매핑"]
end
subgraph 2단계["2단계: checkpoint 발행 + offset 동기화"]
CC["MirrorCheckpointConnector<br/>source consumer 그룹 offset 읽기"] --> OST
OST --> TR["offset 변환<br/>source offset → target offset"]
TR --> CKPT["checkpoints topic<br/>(target에 저장)"]
TR -->|"sync.group.offsets.enabled=true"| TCO["target __consumer_offsets<br/>(직접 기록)"]
end
1단계 — offset-syncs topic: MirrorSourceConnector가 record를 복제할 때마다, source offset과 target offset의 매핑을 mm2-offset-syncs.{target}.internal topic에 기록한다. (MirrorConnectorConfig.java) 이 topic은 기본적으로 source cluster에 저장된다 (offset-syncs.topic.location = source). (MirrorConnectorConfig.java)
2단계 — checkpoint + group offset 동기화: MirrorCheckpointConnector가 source cluster에서 consumer 그룹의 현재 offset을 읽고, offset-syncs topic의 매핑을 이용해 target 기준 offset으로 변환한 뒤:
- checkpoints topic(
{target}.checkpoints.internal)에 변환된 offset을 기록한다 — "source 그룹 X가 source offset 100까지 읽었고, 이는 target offset 97에 해당한다." sync.group.offsets.enabled = true인 경우, 변환된 offset을 target cluster의__consumer_offsetstopic에 직접 기록한다. 이렇게 되면 target cluster로 consumer를 전환했을 때, source에서 읽던 위치부터 자연스럽게 이어서 읽을 수 있다.
(MirrorCheckpointConfig.java)에 따르면,
sync.group.offsets.enabled의 기본값은false다. 의도하지 않은 offset 덮어쓰기를 막기 위해保守的に 기본값이 설정된 것이다. DR 목적이라면 반드시true로 설정해야 한다.
offset 동기화의 치명적인 전제 조건
sync.group.offsets.enabled = true가 동작하려면 "target cluster에 해당 consumer 그룹의 활성 consumer가 없어야 한다" — (MirrorCheckpointConfig.java)의 문서에 명시된 전제 조건이다.
이 조건이 왜 중요한가:
- target에 활성 consumer가 있으면, MM2가 덮어쓰는 offset과 consumer가 자체적으로 관리하는 offset이 충돌한다.
- Active/Passive DR에서는 정상적으로 동작 — 평소 target에 consumer가 없으므로 MM2가 offset을 안전하게 동기화한다.
- Active/Active에서는 제약이 된다 — 양쪽에 consumer가 있으므로 offset 동기화가 제대로 동작하지 않는다.
이 제약 때문에 Active/Active에서는 offset 동기화 대신 checkpoints topic을 직접 조회하여 애플리케이션 수준에서 offset을 복구하는 패턴이 필요하다.
MirrorClientAPI(kafka-clients의org.apache.kafka.connect.mirror.MirrorClient)를 통해 checkpoint를 조회할 수 있다.
offset lag 허용 임계값 — offset.lag.max
source offset을 target offset으로 변환할 때, 변환 데이터가 없는 offset(매핑이 아직 기록되지 않은 최신 영역)는 어떻게 처리되는가. offset.lag.max(기본값: 100) 설정이 이를 제어한다 — 매핑이 없는 offset 차이가 이 값 이하면 가장 가까운 매핑을 사용하고, 초과하면 checkpoint를 생략한다. (MirrorConnectorConfig.java)
너무 낮으면 복제 지연 시 checkpoint가 누락되고, 너무 높으면 정확도가 떨어진다. 처리량이 높은 토픽은 기본값(100)으로 충분하지만, 낮은 처리량 토픽은 조정이 필요할 수 있다.
Active/Active 구성 — 멀티 리전 양방향 복제
Active/Active는 두 리전 모두에서 읽기·쓰기를 수행하면서 데이터를 상호 복제한다.
# Kafka 4.3, KRaft
clusters = us-west, us-east
us-west.bootstrap.servers = broker1-west:9092,broker2-west:9092
us-east.bootstrap.servers = broker1-east:9092,broker2-east:9092
# 양방향 flow
us-west->us-east.enabled = true
us-east->us-west.enabled = true
# 모든 토픽 복제
topics = .*
topics.exclude = .*[\-\.]internal, .*\.replica, __.*
# 내부 topic 복제 팩터
replication.factor = 3
checkpoints.topic.replication.factor = 3
heartbeats.topic.replication.factor = 3
offset-syncs.topic.replication.factor = 3
# checkpoint 발행 (양쪽 consumer 모니터링)
emit.checkpoints.enabled = true
emit.checkpoints.interval.seconds = 60
# offset 동기화는 Active/Active에서는 제약이 있음 (위 참조)
sync.group.offsets.enabled = true
sync.group.offsets.interval.seconds = 60
Active/Active에서 루프 방지를 위해
topics.exclude를 별도로 설정할 필요는 없다 — 같은 설정 파일에 두 flow를 정의하면 MM2가 자동으로us-west.*,us-east.*패턴의 토픽(이미 복제된 토픽)을 되복제하지 않는다. (geo-replication.md)
Active/Active의 consumer 관점
양방향 복제 환경에서 consumer가 foo 토픽을 구독하면, 같은 cluster의 원본 foo와 반대쪽에서 복제된 us-east.foo(또는 us-west.foo) 모두를 구독해야 양쪽 데이터를 모두 받는다. 이를 위해 MM2는 consumer가 하나의 "논리적 토픽"으로 통합 구독할 수 있게 지원하지 않으므로 — 애플리케이션이 두 토픽을 모두 구독하거나, upstream에서 통합 토픽으로 다시 쓰는 별도 계층이 필요하다.
이 한계는 MM2 설계의 트레이드오프다: 단순성(이름 규칙 기반 출처 추적)을 택하는 대신 consumer 복잡성을 감수한다. 대안으로 Kafka 3.9+에서 도입된 Cluster Linking(Confluent 확장, ASF core 아님)이 이 문제를 다르게 접근하지만, 이 글의 범위를 벗어난다.
프로덕션 운영 고려사항
consume from remote, produce to local
공식 문서가 명시하는 최우선 권장 사항이다. (geo-replication.md)
First DC Second DC
========== =================
primary ------------- MM2 ---------> secondary
(remote / source) (local / target)
Kafka producer는 consumer보다 불안정한 네트워크에 취약하다 (ack 대기, 재시도, 타임아웃). 따라서 MM2 프로세스를 target cluster와 같은 위치에 배치하고 --clusters 옵션으로 로컬 target만 지정하는 것이 지연 최소화의 핵심이다.
# secondary DC에서 실행 — primary(원격)에서 읽고 secondary(로컬)로 쓰기
bin/connect-mirror-maker.sh mm2.properties --clusters secondary
tasks.max 설정
MM2는 Connect 기반이므로, tasks.max로 병렬 task 수를 조절한다. 기본값은 1이며, 프로덕션에서는 최소 2 이상을 권장한다 — topic-partition 수와 하드웨어 리소스에 따라 증가. (geo-replication.md)
# 각 MM2 프로세스의 최대 task 수
tasks.max = 5
내부 topic 관리
MM2는 여러 내부 topic을 생성한다. (connect-mirror-maker.properties)
| topic | 위치 | 목적 | 복제 팩터 설정 |
|---|---|---|---|
heartbeats |
target | connector↔cluster 연결 상태 | heartbeats.topic.replication.factor |
{target}.checkpoints.internal |
source (기본) | 변환된 offset checkpoint | checkpoints.topic.replication.factor |
mm2-offset-syncs.{target}.internal |
source (기본) | source→target offset 매핑 | offset-syncs.topic.replication.factor |
Connect 내부 topic (*-configs, *-offsets, *-status) |
target | Connect 프레임워크 상태 | *.storage.replication.factor |
프로덕션에서는 모든 내부 topic의 복제 팩터를 3 이상으로 설정해야 한다. 기본 예제 파일에서는 1로 설정되어 있으나, 이는 개발/테스트용이다.
설정 일관성 — 치명적인 함정
여러 MM2 프로세스가 같은 target cluster를 향해 복제할 때, 설정이 다르면 마지막에 실행된 프로세스의 설정으로 덮어쓰기된다. (geo-replication.md)
# process 1
A->B.enabled = true
A->B.topics = foo
# process 2 (같은 target B를 향함)
A->B.enabled = true
A->B.topics = bar
# 결과: foo 또는 bar 중 하나만 복제됨 (leader에 따라 결정)
→ 모든 MM2 프로세스가 동일한 설정 파일을 사용해야 한다. 조직 수준에서 단일 설정 파일을 관리하고 자동화 도구(Ansible, Kubernetes ConfigMap 등)로 배포하는 것이 안전하다.
exactly-once 지원 (Kafka 3.5+)
dedicated MM2 cluster에 대해 exactly-once semantic이 지원된다 (Kafka 3.5.0부터). (geo-replication.md)
# target cluster에 exactly-once 쓰기
secondary.exactly.once.source.support = enabled
# MM2 노드 간 내부 통신 활성화 (필수)
dedicated.mode.enable.internal.rest = true
listeners = http://localhost:8080
# source consumer에서 aborted transaction 필터링
primary.consumer.isolation.level = read_committed
기존 MM2 cluster를 exactly-once로 전환하려면 2단계 업그레이드가 필요하다: 먼저
exactly.once.source.support = preparing으로 전체 노드 재시작, 이후enabled로 재재시작. (geo-replication.md)
모니터링 — replication-latency가 핵심 메트릭
MM2는 kafka.connect.mirror 메트릭 그룹으로 JMX 메트릭을 발행한다. (geo-replication.md)
# MirrorSourceConnector 메트릭
record-count # 복제된 record 수
record-rate # records/sec
replication-latency-ms # source → target 전파 지연 (핵심)
byte-rate # bytes/sec
# MirrorCheckpointConnector 메트릭
checkpoint-latency-ms # consumer offset 복제 지연
replication-latency-ms는 source에서 record가 쓰인 시각과 target에 복제된 시각의 차이이다. DR 시나리오에서 이 값이 크면, 장애 전환 시 최근 데이터가 유실될 수 있음을 의미한다. Prometheus + Grafana로 replication-latency-ms와 checkpoint-latency-ms를 대시보드에 반드시 포함해야 한다.
console-consumer 테스트 시 주의
기본적으로 MM2는 console-consumer-.*, connect-.*, __.* 패턴의 consumer 그룹을 복제에서 제외한다 (groups.exclude 기본값). 테스트로 console consumer를 실행한 그룹의 offset이 동기화되지 않는다면 이 설정이 원인이다. (geo-replication.md)
테스트 시에는 임시로 제외 목록을 수정:
# 테스트용 — console-consumer 그룹도 동기화
groups.exclude = connect-.*, __.*
테스트 완료 후 반드시 원래대로 복구.
DR 장애 전환(failover) 실제 시나리오
Active/Passive DR에서 장애 전환은 다음 순서로 수행한다:
flowchart TD
A["1. primary 장애 감지"] --> B["2. consumer를 secondary로 전환<br/>(target 토픽명 사용: primary.foo)"]
B --> C["3. 동기화된 offset으로 이어서 소비<br/>(sync.group.offsets=true였으므로 자동)"]
C --> D["4. producer를 secondary로 전환"]
D --> E["5. primary 복구 후<br/>역방향 flow로 데이터 역동기화"]
전환 시 consumer가 구독하는 토픽 이름이 바뀐다 — foo → primary.foo (DefaultReplicationPolicy). 이를 자동화하려면 consumer 설정에서 토픽 이름을 환경 변수로 관리하고, failover 시 이 값을 교체하는 메커니즘이 필요하다.
장애 복구(failback) 후 primary와 secondary 간 데이터 일관성을 맞추려면, 복구된 primary로 역방향 복제 flow를 임시 활성화해야 한다. 단, 이미 소비된 offset 이후의 데이터만 복제되도록 주의.
MM2 vs 클러스터 내 복제 — 혼동하면 안 되는 것
| 항목 | 클러스터 내 복제 (ISR/HW) | 클러스터 간 복제 (MM2) |
|---|---|---|
| 목적 | 단일 클러스터 내 broker 간 데이터 안전성 | 서로 다른 클러스터/리전 간 데이터 복제 |
| 단위 | partition replica | topic (데이터 + 설정 + offset + ACL) |
| 지연 | 밀리초 (동기/비동기 복제) | 네트워크 RTT + 복제 파이프라인 지연 |
| offset 보존 | 같은 cluster이므로 동일 | 변환 필요 (source ≠ target offset) |
| 장애 조치 | 자동 (리더 선출) | 수동 또는 반자동 (consumer/producer 전환 필요) |
요약 — 이 글의 결론
- MM2는 Connect 기반 크로스 클러스터 복제 프레임워크다. 데이터뿐 아니라 토픽 설정, ACL, consumer offset까지 복제한다 — 이것이 MirrorMaker 1과의 근본적 차이.
- 복제된 토픽 이름에는 source alias가 붙는다 (
us-west.foo). 이 규칙이 루프 방지와 출처 추적을 가능하게 하지만, consumer는 target에서 다른 이름으로 구독해야 한다. - offset 동기화는
sync.group.offsets.enabled = true로 명시적 활성화해야 한다 (기본값 false). 핵심 전제: target에 활성 consumer가 없어야 동작한다 — Active/Passive DR에는 적합, Active/Active에는 제약. - consume from remote, produce to local — MM2 프로세스는 target 근처에 배치한다. producer가 consumer보다 네트워크 지연에 취약하기 때문.
- 설정 일관성이 치명적이다 — 같은 target을 향하는 모든 MM2 프로세스는 동일한 설정 파일을 써야 한다. 다르면 리더 선출에 따라 일부 복제가 조용히 사라진다.
- DR 장애 전환은 자동이 아니다 — 토픽 이름 변경, consumer/producer 재연결, offset 검증을 포함한 런북(runbook)이 있어야 한다.
생각해 볼 문제
- Active/Active 환경에서 consumer가 source의
foo와 복제된us-east.foo를 모두 구독하고 있다. 같은 record를 두 번 처리하지 않으려면 애플리케이션 수준에서 어떤 설계가 필요할까? sync.group.offsets.enabled = true인데 DR 전환 후 consumer가 offset 0부터 다시 읽는다면, 어떤 원인을 의심해야 할까?- 세 개의 리전(west, east, north)이 있고 각 리전에 두 개의 클러스터가 있다. XDCR(Cross Data Center Replication)을 포함한 전체 복제 토폴로지에서
--clusters옵션 없이 실행하면 어떤 문제가 발생할까? - MM2의 exactly-once가 활성화된 환경에서 source cluster의 producer가 transaction을 abort했다. target에서 이 abort된 데이터가 어떻게 처리되는가?
offset-syncs.topic.location을source에서target으로 변경하면 어떤 장단점이 있을까?
참고
- ASF 공식 문서 - Geo-Replication (Cross-Cluster Data Mirroring) - 접근 2026-07-10
- MirrorMaker Configs - 접근 2026-07-10
- MirrorConnectorConfig.java - 접근 2026-07-10
- MirrorCheckpointConfig.java - 접근 2026-07-10
- DefaultReplicationPolicy.java - 접근 2026-07-10
- connect-mirror-maker.properties 예시 - 접근 2026-07-10
- KIP-382: MirrorMaker 2.0 - 접근 2026-07-10
'Tech Artifacts > Kafka' 카테고리의 다른 글
| Kafka - 12. operations (0) | 2026.07.09 |
|---|---|
| Kafka - 11. kafka streams (0) | 2026.07.09 |
| Kafka - 10. kafka connect (0) | 2026.07.09 |
| Kafka - 09. schema registry (1) | 2026.07.09 |
| Kafka - 08. delivery semantics (0) | 2026.07.09 |
