백엔드 데이터 인프라 129편. Kafka Streams 운영 — SASL_SSL 설정, Internal topic 직접 관리·tuning, kafka-streams-application-reset.sh 로 state 재시작, deploy 전략, version upgrade, 자주 발생하는 운영 사고 패턴까지 풀어쓴 학습 노트. Part 5-10 Streams 마무리.
이 글은 백엔드 데이터 인프라 시리즈 130편 중 129편이에요. Part 5-10 Kafka Streams 의 마지막 글. 127·128편 까지 IQ·Testing 을 잡았다면, 이번 129편은 Production 운영 — Security·Internal Topics·App Reset·Deploy·Upgrade.
1. Security 설정
113~116편 보안 종합 + Streams 특화:
spring:
kafka:
streams:
application-id: my-streams-app
properties:
# SASL_SSL
security.protocol: SASL_SSL
sasl.mechanism: SCRAM-SHA-512
sasl.jaas.config: >
org.apache.kafka.common.security.scram.ScramLoginModule required
username="${KAFKA_STREAMS_USER}"
password="${KAFKA_STREAMS_PASSWORD}";
# SSL
ssl.truststore.location: /etc/kafka/ssl/truststore.jks
ssl.truststore.password: ${TRUSTSTORE_PASSWORD}
# Internal topic 들도 같은 설정
producer.security.protocol: SASL_SSL
producer.sasl.mechanism: SCRAM-SHA-512
producer.sasl.jaas.config: ${KAFKA_JAAS}
producer.ssl.truststore.location: /etc/kafka/ssl/truststore.jks
consumer.security.protocol: SASL_SSL
consumer.sasl.mechanism: SCRAM-SHA-512
consumer.sasl.jaas.config: ${KAFKA_JAAS}
consumer.ssl.truststore.location: /etc/kafka/ssl/truststore.jks
여기서 시험 함정이 하나 있어요 — Streams 가 내부적으로 producer + consumer + admin 모두 사용. 각자 보안 config 명시 필수.
2. ACL 요구사항
ACL(권한 제어 목록)로 Streams app 의 user 에게 줘야 하는 권한:
# Input/output topic
$ kafka-acls.sh --add --allow-principal User:my-streams-user \
--operation Read --topic input-topic \
--operation Write --topic output-topic \
--operation Describe --topic input-topic --topic output-topic
# Internal topics (PREFIXED)
$ kafka-acls.sh --add --allow-principal User:my-streams-user \
--operation All \
--topic "my-streams-app-" --resource-pattern-type PREFIXED \
--group "my-streams-app" \
--transactional-id "my-streams-app" --resource-pattern-type PREFIXED
# Cluster (IdempotentWrite for EOS)
$ kafka-acls.sh --add --allow-principal User:my-streams-user \
--operation IdempotentWrite --cluster
application.id prefix 로 PREFIXED ACL 을 걸면 internal topic 권한이 자동으로 따라붙어요. 참고로 EOS(exactly-once semantics, 정확히 한 번 처리)에는 cluster 의 IdempotentWrite 가 필요해요.
3. Internal Topic 직접 관리
Streams 가 자동 생성:
<app-id>-<store-name>-changelog(state store backup)<app-id>-<store-name>-repartition(groupBy 후 재partition)
기본 설정 자동:
- RF =
replication.factor(Streams config) - Partition = input topic 과 동일
cleanup.policy=compact(changelog) /delete(repartition)
운영 권장 — 미리 생성
자동 생성에 의존하지 않고 미리 생성:
$ kafka-topics.sh --create --topic my-streams-app-word-counts-changelog \
--bootstrap-server localhost:9092 \
--partitions 8 --replication-factor 3 \
--config cleanup.policy=compact \
--config segment.bytes=104857600
장점 — retention·compaction·segment 명시 제어.
Streams 설정 영향
spring:
kafka:
streams:
properties:
replication.factor: 3
topic.replication.factor: 3
min.insync.replicas: 2
# Internal topic 의 cleanup
# changelog 는 자동 compact
# repartition 은 자동 delete (짧은 retention)
4. App Reset Tool
$ kafka-streams-application-reset.sh \
--bootstrap-server localhost:9092 \
--application-id my-streams-app \
--input-topics input-topic \
--intermediate-topics ... \
--to-earliest \
--execute
수행 동작:
- Consumer group offset reset =
--to-earliest(처음부터) 또는--to-datetime등 - Internal topic 삭제 (repartition 등) + 재생성
- Local state store 삭제 (옵션)
Step-by-Step
# 1. App 종료
$ kubectl scale deployment my-streams-app --replicas=0
# 2. Reset (dry-run 먼저)
$ kafka-streams-application-reset.sh ... --dry-run
$ kafka-streams-application-reset.sh ... --execute
# 3. Local state 삭제 (각 instance 에서)
$ rm -rf /var/kafka-streams-state/my-streams-app/
# 4. App 재시작
$ kubectl scale deployment my-streams-app --replicas=N
언제 Reset?
- 로직 변경 + 재처리 필요
- State corruption 복구
- 새 환경 deploy + clean start
- 테스트 후 정리
여기서 정말 중요한 자리 — Reset 전 반드시 app 정지. 실행 중에 돌리면 일관성이 깨져요.
5. Deploy 전략
Rolling Update
# Kubernetes
spec:
strategy:
type: RollingUpdate
rollingUpdate:
maxUnavailable: 1
maxSurge: 1
한 instance 씩 교체해요. num.standby.replicas ≥ 1 에 Cooperative rebalance 를 더하면 무중단이 됩니다.
Blue-Green Deploy (어려움)
Streams 는 같은 application.id 끼리 cluster 를 공유해요. Blue-Green 으로 가려면 다른 application.id 가 되고, 그러면 state 를 새로 빌드해야 합니다.
대신 Rolling update 가 표준.
Canary
소수 instance 만 새 버전. 위험 — state·partition 분담이 두 버전에 걸침. 일반적으로 Streams 는 canary 어려움.
6. Version Upgrade
spring:
kafka:
streams:
properties:
upgrade.from: "3.5" # 옛 버전에서 새 버전으로 upgrade
upgrade.from 에 옛 버전을 명시해 두고, 한 차례 rolling restart 한 뒤에 제거합니다.
Major Version Upgrade 절차
1. 모든 instance 가 v3.5
2. `upgrade.from=3.5` 추가 + 새 버전 (v4.0) 으로 rolling restart
3. 모두 v4.0 으로 안정 확인
4. `upgrade.from` 제거 + 다시 rolling restart
7. Manage Internal Topics
Changelog topic 의 Compaction Lag
log.cleaner.dedupe.buffer.size=104857600
log.cleaner.threads=4
Broker 측 cleaner thread 설정이에요. state store 가 커질수록 cleaner 부담도 같이 늘어요.
Retention 조정
$ kafka-configs.sh --alter --entity-type topics \
--entity-name my-streams-app-store-changelog \
--add-config "min.cleanable.dirty.ratio=0.1,segment.bytes=104857600"
update 가 잦은 환경이면 compaction 도 더 aggressive 하게 가져가요.
8. 자주 발생하는 운영 사고
Issue 1: Consumer lag 폭증
확인:
$ kafka-consumer-groups.sh --bootstrap-server localhost:9092 \
--describe --group my-streams-app
원인:
- Stream thread 부족 →
num.stream.threads늘림 - Processing latency 큰 외부 호출
- State store rebuild
대응:
- Instance 추가
- num.stream.threads 늘림
- Standby replicas 늘림
Issue 2: State restore 너무 김
대량 changelog 처리 = 수 시간 가능. 대응:
num.standby.replicas ≥ 1미리 설정- changelog topic의 compaction 자주
- State store cache 키움
Issue 3: Rebalance 폭증
원인:
max.poll.interval.ms초과- Pod 자주 재시작
- GC pause
대응:
- 87편 rebalance 패턴 + Static Membership
group.instance.id설정- GC tuning
Issue 4: Internal topic 폭증
원인:
- 잘못된
application.id(oldapp + newapp 혼재) - Reset 안 한 채 새 app 배포
대응:
- App Reset Tool
- Internal topic 수동 삭제
Issue 5: EOS 성능 하강
원인:
- transaction commit 빈도 높음
대응:
commit.interval.ms늘림 (100 → 1000)- Production exception handler 자주 호출 시 root cause 해결
9. 모니터링 — 운영 핵심 메트릭
JMX(Java 관리 확장):
| 메트릭 | 목표 |
|---|---|
stream-thread-metrics:process-rate |
일정 throughput |
stream-task-metrics:commit-rate |
1초당 1+ |
| Consumer lag | < 1000 (실시간 환경) |
state-store:put-rate |
일정 |
state-restoration:restore-rate |
재시작 시만 활성 |
record-error-rate |
0 |
Grafana 대시보드 (공개 dashboard 활용).
10. Production Checklist
배포 전:
- [ ]
application.idcluster unique - [ ] EOS V2 활성 (
processing.guarantee=exactly_once_v2) - [ ]
num.standby.replicas ≥ 1 - [ ] Replication factor 3 + min.insync 2
- [ ] Error handlers 명시 (Uncaught·Deserialization·Production)
- [ ] State dir 영구 경로 (
/var/...) - [ ] SASL_SSL + ACL
- [ ]
group.instance.id(Static Membership) - [ ] Internal topics RF 3
- [ ] Monitoring·alerting (JMX·Grafana)
- [ ] Health check (
/actuator/health) - [ ] App Reset 절차 문서화
Part 5-10 Streams 마무리
9편 (121~129):
- 121 Intro — 정체성·KStream/KTable
- 122 Quickstart — WordCount hands-on
- 123 Core Concepts — Topology·Task·Thread·Partition
- 124 Write & Run — Spring Boot·Error Handler·운영
- 125 DSL — filter·map·groupBy·join·window
- 126 Processor API — Low-level·Punctuator·State Store
- 127 Stateful + IQ — Interactive Queries·HTTP endpoint
- 128 Testing — TopologyTestDriver·EmbeddedKafka
- 129 운영 — Security·Manage·Reset·Deploy
Kafka Streams 의 모든 영역. 입문부터 운영까지.
시험 직전 한 번 더 — Streams 운영 함정 압축 노트
- Security = SASL_SSL + SCRAM-SHA-512, producer/consumer/admin 모두 설정
- ACL = input/output Topic + Internal topics (PREFIXED) + Group + TransactionalId + Cluster (IdempotentWrite for EOS)
- Internal Topics =
<app-id>-<store>-changelog/repartition자동 - 운영 권장 = 미리 생성 (retention·compaction 명시)
replication.factor: 3+min.insync.replicas: 2- App Reset Tool =
kafka-streams-application-reset.sh - 동작 = consumer group offset reset + internal topic 삭제·재생성 + local state 삭제 (옵션)
- 반드시 app 정지 후 실행
- Rolling Update =
num.standby.replicas ≥ 1+ Cooperative rebalance - Blue-Green X (application.id 같으면 state 공유)
- Canary 어려움
- Version Upgrade =
upgrade.from추가 + 새 버전 rolling restart + 제거 + 다시 rolling - 자주 사고 — Consumer lag·State restore 길음·Rebalance storm·Internal topic 폭증·EOS 성능
- Production Checklist — application.id unique·EOS V2·standby ≥ 1·RF 3·Error handlers·state dir 영구·SASL_SSL·ACL·group.instance.id·Internal RF 3·monitoring·health check
- 모니터링 — process-rate·commit-rate·consumer lag·state put-rate·restore-rate·error-rate
- Part 5-10 Streams 9편 = Intro·Quickstart·Core Concepts·Write/Run·DSL·Processor·Stateful/IQ·Testing·운영
공식 문서: Kafka Streams Manage Streams Application 에서 자세한 운영 사양을 확인할 수 있어요.
시리즈 다른 편 (앞뒤 글 모음)
이전 글:
- 124편 — Kafka Streams Write & Run (Spring Boot · 운영 패턴)
- 125편 — Kafka Streams DSL (변환·집계·Join·Window)
- 126편 — Kafka Streams Processor API (Low-Level)
- 127편 — Kafka Streams Stateful + Interactive Queries
- 128편 — Kafka Streams Testing (TopologyTestDriver)
다음 글: