Deploy Kafka on Kubernetes โธ
๋ค์ด๊ฐ๋ฉฐ
ํ์ฌ์์ Confluent๋ฅผ ํตํด Kafka ํด๋ฌ์คํฐ๋ฅผ ์ ์ฌ์ฉํ๊ณ ์์์ต๋๋ค. ๊ทธ๋ฐ๋ฐ, ์ด ์นดํ์นด์ ๋ํด์ ์ข๋ ์์ธํ ์๊ณ , ์ ๋ฌธ์ฑ์ ๊ฐ์ถ๊ณ ์ถ๋ค๋ ์๊ฐ์ด ๋ค์ด์ 2025๋ ์ฒซ ๋ชฉํ๋ก Confluent์ Kafka ์๊ฒฉ์ฆ์ธ Confluent Certified Developer for Apache Kafkaยฎ ์๊ฒฉ์ฆ์ ์ค๋นํ๊ณ ์์ต๋๋ค โ๏ธ
์ง๊ธ๊น์ง Confluent ์์์ Saas๋ก๋ง Kafka๋ฅผ ์ด์ํด๋ณธ ๊ฒ ๊ฐ์์, ์ํ๋ ์ค๋นํด๋ณผ๊ฒธ! Kubernetes์์ Kafka Cluster๋ฅผ ์ด์ํด๋ณด๋ฉฐ ์ด๋ฆฌ์ ๋ฆฌ ๋ง๋ณด๊ณ ์ ํฉ๋๋ค ใ ใ
์ผ๋จ ๋ํ๋ก์ด๋ฅผ ํด๋ณด์!
์ ๋ ์ฃผ๋ก Helm Chart๋ก ์ํฌ๋ก๋๋ฅผ ๋ํ๋ก์ดํ๊ธฐ ๊ด๋ฆฌํ๊ณ ์์ต๋๋ค. ์ด๋ฒ์๋ Helm Chart๋ฅผ ์ด์ฉํด Kafka๋ฅผ ๋ํ๋ก์ด ํด๋ณด๊ฒ ์ต๋๋ค! ์๋์ ๊ฐ์ด helmfile.bitnami-kafka.yaml
์ ์ค๋นํฉ๋๋ค.
# @helmfile.bitnami-kafka.yaml
repositories:
- name: bitnami
url: https://charts.bitnami.com/bitnami
releases:
- name: bitnami-kafka
namespace: kafka
chart: bitnami/kafka
version: 31.1.1
values:
- ./values.bitnami-kafka.yaml
bitnami/kafka
์ฐจํธ ๊ทธ๋๋ก ๋ํ๋ก์ด ํด๋ ๋ฉ๋๋ค๋ง, ๊ทธ๋๋ก ํ๋ Kraft ๋ชจ๋๋ก ๋ํ๋ก์ด ๋๋๋ผ๊ตฌ์! ์ ๋ ์ผ๋จ Zookeeper ๋ชจ๋๋ถํฐ ํ
์คํธ ํด๋ณด๊ธฐ ์ํด ์ปค์คํ
์ด ํ์ํฉ๋๋ค! ๊ทธ๋์ values.bitnami-kafka.yaml
ํ์ผ์ ๋ง๋ค๊ณ ์๋์ ๊ฐ์ด ์์ฑํฉ๋๋ค.
# @values.bitnami-kafka.yaml
zookeeper:
enabled: true
replicaCount: 1
broker:
replicaCount: 3
controller:
replicaCount: 0
kraft:
enabled: false
ํฌ์คํธ๋ฅผ ์ฒ์ ์์ฑํ ๋๋ broker.replicaCount=1
๋ก ์ค์ ํ์ต๋๋ค๋งโฆ ๊ทธ๋ ๊ฒ ํ๋ ๋์ค์ ๋ด๋ถ์ฉ ํ ํฝ์ธ __consumer_offsets
ํ ํฝ ๋ง๋ค๋, replication.factor=3
๋๋ฌธ์ ์ปจ์๋จธ ์ชฝ์ ์ค๋ฅ๊ฐ ์๊ธฐ๋๋ผ๊ตฌ์โฆ ๊ทธ๋์ ์ํ์ฐฉ์ค๋ฅผ ์์น ์์ผ์ ๋ค๋ฉด broker.replicaCount=3
์ผ๋ก ์์ํ๊ธธ ๊ถ์ฅํฉ๋๋ค!
๊ทธ๋ฆฌ๊ณ ์๋ ๋ช ๋ น์ด๋ก ๋ํ๋ก์ด ํ๋ฉด
$ helmfile -f helmfile-kafka.yaml apply`
...
** Please be patient while the chart is being deployed **
Kafka can be accessed by consumers via port 9092 on the following DNS name from within your cluster:
bitnami-kafka.kafka.svc.cluster.local
Each Kafka broker can be accessed by producers via port 9092 on the following DNS name(s) from within your cluster:
bitnami-kafka-broker-0.bitnami-kafka-broker-headless.kafka.svc.cluster.local:9092
The CLIENT listener for Kafka client connections from within your cluster have been configured with the following security settings:
- SASL authentication
To connect a client to your Kafka, you need to create the 'client.properties' configuration files with the content below:
security.protocol=SASL_PLAINTEXT
sasl.mechanism=SCRAM-SHA-256
sasl.jaas.config=org.apache.kafka.common.security.scram.ScramLoginModule required \
username="user1" \
password="$(kubectl get secret bitnami-kafka-user-passwords --namespace kafka -o jsonpath='{.data.client-passwords}' | base64 -d | cut -d , -f 1)";
To create a pod that you can use as a Kafka client run the following commands:
kubectl run bitnami-kafka-client --restart='Never' --image docker.io/bitnami/kafka:3.9.0-debian-12-r4 --namespace kafka --command -- sleep infinity
kubectl cp --namespace kafka /path/to/client.properties bitnami-kafka-client:/tmp/client.properties
kubectl exec --tty -i bitnami-kafka-client --namespace kafka -- bash
PRODUCER:
kafka-console-producer.sh \
--producer.config /tmp/client.properties \
--bootstrap-server bitnami-kafka.kafka.svc.cluster.local:9092 \
--topic test
CONSUMER:
kafka-console-consumer.sh \
--consumer.config /tmp/client.properties \
--bootstrap-server bitnami-kafka.kafka.svc.cluster.local:9092 \
--topic test \
--from-beginning
$ kgp
NAME READY STATUS RESTARTS AGE
bitnami-kafka-zookeeper-0 1/1 Running 0 100s
bitnami-kafka-broker-0 1/1 Running 2 (35s ago) 100s
bitnami-kafka-broker-2 1/1 Running 2 (35s ago) 100s
bitnami-kafka-broker-3 1/1 Running 2 (35s ago) 100s
์ง์! zookeeper ํ๋์ broker ํ๋๊ฐ ๋ํ๋ก์ด ๋์์ต๋๋ค!
์ด๊ฒ zookeeper๋ broker๊ฐ ๊ฐ์ด ๋จ๊ฒ ๋๋๋ฐ, zookeeper๊ฐ ์์ง ์ค๋น๋์ง ์์ ์ํ์์ broker๊ฐ ๋ํ๋ก์ด ๋์ด์ broker๊ฐ ๋ช๋ฒ RESTART
ํ๊ฒ ๋๋๋ฐ, zookeeper๊ฐ ๋ํ๋ก์ด ๋๋ฉด broker๋ ๊ณง RUNNING
์ํ๊ฐ ๋ฉ๋๋ค ใ
ใ
๊ทธ๋ฆฌ๊ณ ๋ญ๊ฐ ์ค๋ช ๋ค์ด ์ญ ๋์ค๋๋ฐ์! ๋ํ๋ก์ด ํ Kafka ํด๋ฌ์คํฐ์ ์ ์ํ๋ ๋ฐฉ๋ฒ์ด ์ ํ ์์ต๋๋ค ใ ใ
Letโs Access the cluster!
๋ํ๋ก์ดํ Kafka ํด๋ฌ์คํฐ์ ์ ์ํด๋ด
์๋ค! Kafka ํด๋ฌ์คํฐ์ ์ ์ํ๋ ๋ฐฉ๋ฒ์ ์ฌ๋ฌ ๊ฐ์ง๊ฐ ์์ง๋ง! ์ ๊ฐ Kafka CLI ๋์ ํธํ๊ฒ ์ฌ์ฉํ๊ณ ์๋ kcat
์ ํตํด ํ๋ฒ ์ ์ํด๋ณด๊ฒ ์ต๋๋ค.
# port-forward๋ฅผ ๋จผ์ ํด์ค์ผ ํฉ๋๋ค.
$ kubectl port-forward svc/bitnami-kafka -n kafka 9092:9092
...
$ kcat -b localhost:9092 -L \
-X security.protocol=SASL_PLAINTEXT \
-X sasl.mechanisms=SCRAM-SHA-256 \
-X sasl.username=user1 \
-X sasl.password=PASSWORD
Metadata for all topics (from broker -1: sasl_plaintext://localhost:9092/bootstrap):
1 brokers:
broker 100 at bitnami-kafka-broker-0.bitnami-kafka-broker-headless.kafka.svc.cluster.local:9092 (controller)
0 topics:
sasl.password
๊ฐ์ ์๊น bitnami/kafka๋ฅผ ๋ํ๋ก์ด ํ ํ์ ๋์จ ๊ฐ์ด๋์ ๋ช
๋ น์ด๋ก ๊ฐ์ ธ์ค๋ฉด ๋ฉ๋๋ค.
$ kubectl get secret bitnami-kafka-user-passwords --namespace kafka -o jsonpath='{.data.client-passwords}' | base64 -d
Kafka UI ๋ํ๋ก์ด
Kafka UI
๋ํ๋ก์ดํ Kafka ํด๋ฌ์คํฐ๋ฅผ ์ข๋ ํธํ๊ณ ์ฝ๊ฒ ๊ด๋ฆฌํ๊ธฐ ์ํด Kafka UI๋ฅผ ์ถ๊ฐ๋ก ๋ํ๋ก์ด ํฉ๋๋ค. ์๊ฑด Apache Kafka์ ๊ณต์ ์ปดํฌ๋ํธ๋ ์๋์ง๋ง! Confluent ํ๋ซํผ ์ฒ๋ผ Kafka ํด๋ฌ์คํฐ๋ฅผ ์น ์ฝ์์์ ๊ด๋ฆฌํ ์ ์๊ฒ ๋์์ค๋๋ค! ๐ซฐ
๋ํ๋ก์ด๋ฅผ ์ํด ์ผ๋จ helmfile์ ์๋์ ๊ฐ์ด ๊ตฌ์ฑํฉ๋๋ค.
# @helmfile.kafka-ui.yaml
repositories:
- name: kafka-ui
url: https://provectus.github.io/kafka-ui-charts
releases:
- name: kafka-ui
namespace: kafka
chart: kafka-ui/kafka-ui
version: 0.7.6
values:
- ./values.kafka-ui.yaml
๊ทธ๋ฆฌ๊ณ values.kafka-ui.yaml
์ bitnami-kafka์ ์ ์ํ๊ธฐ ์ํ SASL ๋ก๊ทธ์ธ ์ ๋ณด๋ฅผ ๊ธฐ์
ํฉ๋๋ค.
# @values.kafka-ui.yaml
yamlApplicationConfig:
kafka:
clusters:
- name: bitnami-kafka
bootstrapServers: bitnami-kafka.kafka.svc.cluster.local:9092
properties:
security.protocol: SASL_PLAINTEXT
sasl.mechanism: SCRAM-SHA-256
sasl.jaas.config: org.apache.kafka.common.security.scram.ScramLoginModule required username="user1" password="PASSWORD";
auth:
type: disabled
management:
health:
ldap:
enabled: false
๋ง์ฐฌ๊ฐ์ง๋ก SASL password๋ bitnami-kafka ํด๋ฌ์คํฐ ์์ฑ ๋, ๋ฐ๊ธํ K8s Secret์ ๊ฐ์ ๊ฐ์ ธ์ ์ฌ์ฉํฉ๋๋ค.
๊ทธ๋ฆฌ๊ณ helmfile apply
๋ก ๋ํ๋ก์ด ํ ํ์! port-forward
๋ก kafka-ui๋ฅผ http://localhost:8080
์์ ์ ์ํด๋ด
์๋ค!
$ kubectl get svc -n kafka
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
bitnami-kafka-broker-headless ClusterIP None <none> 9094/TCP,9092/TCP 122m
bitnami-kafka-zookeeper-headless ClusterIP None <none> 2181/TCP,2888/TCP,3888/TCP 122m
bitnami-kafka-zookeeper ClusterIP 10.43.190.250 <none> 2181/TCP 122m
bitnami-kafka ClusterIP 10.43.176.10 <none> 9092/TCP 122m
kafka-ui ClusterIP 10.43.177.29 <none> 80/TCP 7s
$ kubectl port-forward svc/kafka-ui -n kafka 8080:80
Kafka UI
ใ ใ ์๋ ๊ฒ Kafka ํด๋ฌ์คํฐ์ ๋ํ ์ ๋ณด๋ฅผ ์น ์ฝ์๋ก ํ์ธํ ์ ์์ต๋๋ค!
Kafka UI์ Kafka ๋ธ๋ก์ปค ์๋ฒ ์ธ์๋ Zookeeper๋ Schema Registry, Ksql๋ ์ฐ๊ฒฐํ ์ ์๋ ๊ฒ ๊ฐ์ต๋๋ค. ์ ๋ ์ด๋ฒ ํฌ์คํธ๋ฅผ ์์ฑํ๋ฉด์ ์ฒ์ ์ฌ์ฉํด๋ณด์๋๋ฐ์! ์ถํ์ Kafka UI๋ฅผ ์๋ฆฌ์กฐ๋ฆฌ ๋ฏ์ด๋ณด๊ณ ํฌ์คํธ๋ฅผ ๋ ํ๋ ์์ฑํด๋ณด๊ฒ ์ต๋๋ค ใ ใ
Kafka UI์ Kafka ํด๋ฌ์คํฐ์ ์ฐ๊ฒฐ์ ๋ํ ๋ ์ธ๋ถ์ ์ธ ๋ด์ฉ์ด ํ์ํ๋ค๋ฉด, Kafka UI์ ์ ๋ฌธ์๋ฅผ ์ฐธ๊ณ ํ์๊ธธ ๋ฐ๋๋๋ค ๐ kafka-ui/Misc configuration properties
๋์ ํ ์คํธ
๋ํ๋ก์ดํ Kafka ํด๋ฌ์คํฐ๊ฐ ์ ๋์ํ๋์ง ํ ์คํธ ํด๋ด ์๋ค!
์ฒ์์ bitnami-kafka ํด๋ฌ์คํฐ๋ฅผ ๋ํ๋ก์ด ํ ํ์ ๋์ค๋ ๊ฐ์ด๋๋ฅผ ๋ฐ๋ผ kubernetes์ kafka-client
๋ผ๋ pod์ ํ๋ ๋ ๋ํ๋ก์ด ํฉ๋๋ค.
์ด Pod์ bitnami/kafka
์ด๋ฏธ์ง๋ฅผ ์ฌ์ฉํ์ง๋ง, --command sleep infinity
๋๋ฌธ์ Kafka ํด๋ฌ์คํฐ๋ก ๋์ํ์ง๋ ์์ต๋๋ค. (์ด ๊ณผ์ ์ ๊ท์ฐฎ๋ค๋ฉด, ๊ทธ๋ฅ ํด๋ฌ์คํฐ๋ฅผ ์ด๋ฃจ๋ ๋ธ๋ก์ปค ์ค ํ๋๋ฅผ ์ฌ์ฉํ์
๋ ๋ฌด๋ฐฉํฉ๋๋ค ใ
ใ
)
$ kubectl run bitnami-kafka-client --restart='Never' --image docker.io/bitnami/kafka:3.9.0-debian-12-r4 --namespace kafka --command -- sleep infinity
๊ฐ์ด๋์ ๋ฐ๋ผ client.properties
๋ผ๋ ํ์ผ์ ๋ง๋ค์ด ์๋์ ๊ฐ์ด ์ฑ์๋๋ค.
security.protocol=SASL_PLAINTEXT
sasl.mechanism=SCRAM-SHA-256
sasl.jaas.config=org.apache.kafka.common.security.scram.ScramLoginModule required \
username="user1" \
password="PASSWORD";
PASSWORD
๊ฐ์ kubectl get secret bitnami-kafka-user-passwords --namespace kafka -o jsonpath='{.data.client-passwords}' | base64 -d
๋ช
๋ น์ด๋ก ๊ฐ์ ธ์ต๋๋ค.
์์ฑํ client.properties
ํ์ผ์ kafka-client
Pod ์์ ๋ณต์ฌํฉ๋๋ค.
$ kubectl cp --namespace kafka ./client.properties bitnami-kafka-client:/tmp/client.properties
๊ทธ๋ฆฌ๊ณ ์๋ ๋ช ๋ น์ด๋ก Kafka ํด๋ฌ์คํฐ์ ์ ์ํด๋ด ์๋ค!
$ kubectl exec -it bitnami-kafka-client --namespace kafka -- sh
์ด์ ์๋ ๊ณผ์ ์ ๋ฐ๋ผํ๋ฉฐ ์ค์ต ํด๋ด ์๋ค!
Topic CRUD
์๋ ๋ช ๋ น์ด๋ก ํ ํฝ์ ์์ฑํฉ๋๋ค.
$ kafka-topics.sh \
--bootstrap-server bitnami-kafka.kafka.svc.cluster.local:9092 \
--command-config /tmp/client.properties \
--create \
--replication-factor 1 \
--partitions 2 \
--topic test-topic
Created topic test-topic.
๋ณดํต replication.factor=3
์ ๋๋ก ์ค์ ํ์ง๋ง, ์ง๊ธ ๋์ด Kafka ํด๋ฌ์คํฐ์๋ ๋ธ๋ก์ปค๊ฐ ํ๋ ๋ฟ์ด๊ธฐ ๋๋ฌธ์ replication.factor=1
๋ง ๊ฐ๋ฅํฉ๋๋ค.
๊ทธ๋ฆฌ๊ณ --list
๋ก ํ์ธํด๋ณด๋ฉด
$ kafka-topics.sh \
--bootstrap-server bitnami-kafka.kafka.svc.cluster.local:9092 \
--command-config /tmp/client.properties \
--list
test-topic
๋ฐฉ๊ธ ์์ฑํ ํ ํฝ์ด ์ ์ถ๋ ฅ ๋ฉ๋๋ค ใ ใ
ํ ํฝ ์ญ์ ๋ ์๋์ ๋ช ๋ น์ด๋ก ์ํํฉ๋๋ค.
$ kafka-topics.sh \
--bootstrap-server bitnami-kafka.kafka.svc.cluster.local:9092 \
--command-config /tmp/client.properties \
--delete \
--topic test-topic
๋ค์ --list
๋ก ํ์ธํด๋ณด๋ฉด, ํ ํฝ์ด ์ถ๋ ฅ์์ ์ฌ๋ผ์ ธ ์์ต๋๋ค ใ
ใ
Console Producer/Consumer
๋ค์ --create
๋ก test-topic
์ ๋ง๋ค์ด์ค๋๋ค.
$ kafka-topics.sh \
--bootstrap-server bitnami-kafka.kafka.svc.cluster.local:9092 \
--command-config /tmp/client.properties \
--create \
--replication-factor 1 \
--partitions 2 \
--topic test-topic
Created topic test-topic.
kafka-console-producer.sh
๋ฅผ ์ฌ์ฉํ๋ฉด, ์ฝ์ ์
๋ ฅ์ผ๋ก Topic์ ๋ฐ์ดํฐ๋ฅผ ๋ณด๋ผ ์ ์์ต๋๋ค ใ
ใ
$ kafka-console-producer.sh \
--bootstrap-server bitnami-kafka.kafka.svc.cluster.local:9092 \
--producer.config /tmp/client.properties \
--topic test-topic
>hahaha
>hhohohoh
>merong
์์์ ๋ํ๋ก์ดํ Kafka UI์์ ํด๋น ํ ํฝ์ ๋ฐ์ดํฐ๊ฐ ์ ๋ค์ด๊ฐ๋์ง ํ์ธ ํด๋ณผ์ ์์ต๋๋ค ใ ใ
Kafka UI์์ ํ์ธํ ๋ชจ์ต
์ด๋ฒ์๋ kafka-console-consumer.sh
๋ก ํด๋น ํ ํฝ์ ๋ฐ์ดํฐ๋ฅผ ์ฝ์์ ์ถ๋ ฅํ๋๋ก Subscribe ํด๋ด
์๋ค. ๐
$ kafka-console-consumer.sh \
--consumer.config=/tmp/client.properties \
--bootstrap-server bitnami-kafka.kafka.svc.cluster.local:9092 \
--from-beginning \
--topic=test-topic
hahaha
hhohohoh
merong
Deploy without Auth
๊ทธํ์ ๋ก์ปฌ์์ Kafka ํด๋ฌ์คํฐ๋ฅผ ๋ํ๋ก์ด ํด ์ฐ์ต์ ํด๋ณด๋, ๋ก์ปฌ Kafka ํด๋ฌ์คํฐ์์ SASL Auth ์์ด ์ ์ํ๋๊ฒ Kafka๋ฅผ ์ตํ๋๋ฐ ๋ ๋์์ด ๋๋ ๊ฒ ๊ฐ์ต๋๋คโฆ ๊ทธ๋์ bitnami-kafka๋ฅผ ๋ํ๋ก์ด ํ ๋ ์ฌ์ฉํ values.bitnami-kafka.yaml
ํ์ผ์ listerners
๋ถ๋ถ์ ์๋์ ๊ฐ์ด ์ถ๊ฐํฉ๋๋ค.
# @values.bitnami-kafka.yaml
zookeeper:
enabled: true
replicaCount: 1
broker:
replicaCount: 3
controller:
replicaCount: 0
kraft:
enabled: false
listeners:
client:
protocol: 'PLAINTEXT'
controller:
protocol: 'PLAINTEXT'
๊ทธ๋ฆฌ๊ณ ๋ํ๋ก์ด ํ๋ฉด, SASL ์ธ์ฆ ์์ด๋ Kafka ํด๋ฌ์คํฐ์ ์ ์ํ ์ ์์ต๋๋ค ใ ใ
๋ ๋์๊ฐ๊ธฐ
์ด๋ฒ ํฌ์คํธ์์๋ bitnami์ helm chart๋ฅผ ์ฌ์ฉํด Kafka ํด๋ฌ์คํฐ๋ฅผ Kubernetes์์ ๊ตฌ์ถ ํด๋ณด์์ต๋๋ค! ๋ฌผ๋ก ์ ๋ Confluent ํ๋ซํผ์์ Kafka๋ฅผ ์ฐ๊ธฐ ๋๋ฌธ์ ์๊ฑธ ์ ๋ฌด์์ ํด๋ณผ ๊ธฐํ๋ ์๊ฒ ์ง๋ง! ์ญ์ ์ค์ต์์ ๋ค์ํ ์ ๋ณด์ ๋ ธํ์ฐ๋ค์ด ์๊ฒจ๋๋ ๊ฒ ๊ฐ์ต๋๋ค ใ ใ
์๋๋ ์ด๋ฒ ํฌ์คํธ ์ดํ์ ์งํํด๋ณด๋ ค๊ณ ํ๋ ๊ฒ๋ค ์ ๋๋ค!
- Strimzi์ Strimzi Operator ๋ฐฉ์์ผ๋ก Kafka on K8s ๊ตฌํํ๊ธฐ
- Kafka ์ชฝ์์๋ ์ Strimzi์ ๋์์ ๋ฐ์ ๋ํ๋ก์ด ํ๋ ๊ฒฝ์ฐ๊ฐ ๋ง์ด ๋ณด์์ต๋๋ค.
- ์ด๋ฒ ๊ธฐํ์ ํ๋ฒ ์จ๋ณด๋ฉด ์ฌ๋ฐ์ ๊ฒ ๊ฐ๋ค์ ใ ใ
- KRaft ๋ชจ๋
- ์ด๋ฒ์๋ Zookeeper ๋ชจ๋๋ก Kafka ํด๋ฌ์คํฐ๋ฅผ ๋ํ๋ก์ด ํ์์ต๋๋ค.
- Zookeeper๋ฅผ ์ฐ์ง ์๊ณ Kafka ํด๋ฌ์คํฐ๋ฅผ ์ด์ํ๋ KRaft ๋ชจ๋๋ ํ๋ฒ ์ค์ต ํด๋ณด๊ฒ ์ต๋๋ค ใ ใ
- Kafka UI Deep Dive
- ์ ํฌ์คํธ๋ฅผ ์์ฑํ๋ฉด์, Kafka UI๋ฅผ ์ฒ์ ์ฌ์ฉํด๋ณด์๋๋ฐ์!
- ์ด๊ฒ์ ๊ฒ ๋ง์ ธ๋ณด๋ฉด์ Kafka ํด๋ฌ์คํฐ ์ด์์ ๋ํ ๊ฐ์ ์ข ์ก์๋ณด๊ณ ์ ํฉ๋๋ค ใ ใ
์ ๋ ์ ๋ฒ์ฃผ์ Aํ ๋ ๊ฐ์ ๊ฑธ๋ฆฌ๊ณ ๋ง์๋๋ฐ์! ๐ค ์์ํ๋ค๊ณ ๋ฐ์ ์ ๋๊ฐ์ ๊ทธ๋ฐ์ง ์ค๋ซ๋์ ๋ฌตํ ๋๋ ์ ๊ธ์ ์์ฑํ ์ ์์์ต๋๋ค ใ ใ 2025๋ ์ฌ ํํด๋ ์ฌ๋ฐ๋ ๊ฒ๋ค ๋ง์ดํ๊ณ , ๊ฑด๊ฐํ ํ ํด๊ฐ ๋ ์ ์๊ธธ! ๐