Apache Kafka 4.1.1 部署全指南:容器版 & 二进制版(KRaft 模式)

本文基于 Apache Kafka 4.1.1,默认使用 KRaft 模式(无 ZooKeeper),涵盖两种典型部署方式:

  • 使用 官方 Docker 镜像 apache/kafka:4.1.1 的容器化部署
  • 使用 二进制 tar 包 的传统部署(systemd 管理)

0. 适用读者 & 环境假设

适用读者:

  • 需要在测试 / 生产环境部署 Kafka 的后端 / 大数据 / 运维同学
  • 已有 Docker / Linux 基础,想快速上手 Kafka 4.x(KRaft)

环境假设:

  • OS:Linux x86_64(CentOS 7/8、Rocky、Ubuntu、麒麟 V10 等)
  • Kafka:4.1.1(自带 KRaft,仅支持 KRaft,无 ZooKeeper)
  • JDK:OpenJDK 11 或 17
  • 防火墙允许访问相关端口:9092(客户端)、9093(Controller 内部选举)

1. Kafka 4.1.1 与 KRaft 简要说明

从 Kafka 4.0 开始,官方移除 ZooKeeper 支持,只保留 KRaft 模式。简单理解:

  • KRaft(Kafka Raft) = Kafka 内置的元数据管理与选举机制,用 Raft 共识算法替代 ZooKeeper。
  • 每个 Kafka 进程可以有两种角色:
    • broker:处理客户端读写
    • controller:负责元数据和选举
  • 在小型环境下,一个进程既是 broker 又是 controller;
  • 在生产环境中,可以将 controller 独立出来提升可靠性。

KRaft 核心配置关键词(后面会多次出现):

  • process.roles / KAFKA_PROCESS_ROLES:进程角色
  • node.id / KAFKA_NODE_ID:节点 ID(整型,集群唯一)
  • controller.quorum.voters / KAFKA_CONTROLLER_QUORUM_VOTERS:控制器投票集
  • listeners / KAFKA_LISTENERS:监听地址
  • advertised.listeners / KAFKA_ADVERTISED_LISTENERS:对外公布地址(客户端连接用)

2. 容器版部署:官方 apache/kafka:4.1.1

容器方案非常适合本地开发、测试环境和 CI 场景。Kafka 4.x 官方已经提供了 JVM 版 Docker 镜像 apache/kafka,并在 Quickstart 中给出了典型配置示例。

2.1 使用 docker-compose 快速启动单机 Kafka(推荐)

新建目录,例如:

mkdir -p ~/kafka-4.1.1-docker && cd ~/kafka-4.1.1-docker

新建 docker-compose.yml

services:
  broker:
    image: apache/kafka:4.1.1
    hostname: broker
    container_name: broker
    ports:
      - "9092:9092"
    environment:
      # Broker 基本信息
      KAFKA_BROKER_ID: 1

      # 三种监听:
      # - PLAINTEXT:集群内部使用
      # - CONTROLLER:KRaft controller 通讯
      # - PLAINTEXT_HOST:宿主机客户端访问
      KAFKA_LISTENER_SECURITY_PROTOCOL_MAP: PLAINTEXT:PLAINTEXT,PLAINTEXT_HOST:PLAINTEXT,CONTROLLER:PLAINTEXT
      KAFKA_LISTENERS: PLAINTEXT://broker:29092,CONTROLLER://broker:29093,PLAINTEXT_HOST://0.0.0.0:9092
      KAFKA_ADVERTISED_LISTENERS: PLAINTEXT://broker:29092,PLAINTEXT_HOST://localhost:9092

      # KRaft 相关
      KAFKA_PROCESS_ROLES: broker,controller
      KAFKA_NODE_ID: 1
      KAFKA_CONTROLLER_QUORUM_VOTERS: 1@broker:29093
      KAFKA_CONTROLLER_LISTENER_NAMES: CONTROLLER

      # 日志目录(容器内路径,可按需用 volume 映射出来)
      KAFKA_LOG_DIRS: /tmp/kraft-combined-logs

      # 单机环境下的 Topic 副本相关(生产环境不要用 1)
      KAFKA_OFFSETS_TOPIC_REPLICATION_FACTOR: 1
      KAFKA_TRANSACTION_STATE_LOG_MIN_ISR: 1
      KAFKA_TRANSACTION_STATE_LOG_REPLICATION_FACTOR: 1
      KAFKA_GROUP_INITIAL_REBALANCE_DELAY_MS: 0

      # 集群 ID(任意合法值,但整个集群需保持一致)
      CLUSTER_ID: MkU3OEVBNTcwNTJENDM2Qk

上面这份 compose 文件基本与官方 Quickstart 一致,只是把镜像版本固定为 4.1.1,方便环境可控。

启动:

docker compose up -d

检查容器状态:

docker ps
# 正常情况下可以看到 broker 容器

2.2 在容器里测试 Kafka

进入容器:

docker exec -it broker bash

在容器内执行以下命令即可:

2.2.1 创建 Topic
kafka-topics   --create   --topic demo-topic   --partitions 3   --replication-factor 1   --bootstrap-server localhost:9092
2.2.2 发送消息(生产者)
kafka-console-producer   --topic demo-topic   --bootstrap-server localhost:9092
# 输入几行数据,例如:
# hello kafka
# kafka 4.1.1 kraft
# 然后 Ctrl+C 退出
2.2.3 消费消息(消费者)
kafka-console-consumer   --topic demo-topic   --from-beginning   --bootstrap-server localhost:9092

如果能看到刚才发的所有消息,说明容器版 Kafka 工作正常。

2.3 使用 docker run 一条命令起 Kafka(备选)

如果你不想写 compose,也可以直接用 docker run

docker run -d   --name kafka-4.1.1   -p 9092:9092   apache/kafka:4.1.1   sh -c '
    export KAFKA_BROKER_ID=1 &&     export KAFKA_LISTENER_SECURITY_PROTOCOL_MAP=PLAINTEXT:PLAINTEXT,PLAINTEXT_HOST:PLAINTEXT,CONTROLLER:PLAINTEXT &&     export KAFKA_LISTENERS=PLAINTEXT://kafka-4.1.1:29092,CONTROLLER://kafka-4.1.1:29093,PLAINTEXT_HOST://0.0.0.0:9092 &&     export KAFKA_ADVERTISED_LISTENERS=PLAINTEXT://kafka-4.1.1:29092,PLAINTEXT_HOST://localhost:9092 &&     export KAFKA_PROCESS_ROLES=broker,controller &&     export KAFKA_NODE_ID=1 &&     export KAFKA_CONTROLLER_QUORUM_VOTERS=1@kafka-4.1.1:29093 &&     export KAFKA_CONTROLLER_LISTENER_NAMES=CONTROLLER &&     export KAFKA_LOG_DIRS=/tmp/kraft-combined-logs &&     export KAFKA_OFFSETS_TOPIC_REPLICATION_FACTOR=1 &&     export KAFKA_TRANSACTION_STATE_LOG_MIN_ISR=1 &&     export KAFKA_TRANSACTION_STATE_LOG_REPLICATION_FACTOR=1 &&     export KAFKA_GROUP_INITIAL_REBALANCE_DELAY_MS=0 &&     export CLUSTER_ID=MkU3OEVBNTcwNTJENDM2Qk &&     /opt/kafka/bin/kafka-server-start.sh /opt/kafka/config/kraft/server.properties
  '

实际使用时更推荐 docker-compose:配置更清晰,也方便扩展多节点。


3. 二进制版本部署:kafka_2.13-4.1.1.tgz

如果你需要更精细的控制(例如配合现有运维体系、统一日志目录、systemd 管理等),可以使用官方二进制包部署。

3.1 安装 JDK 与创建用户

# 以 RHEL/CentOS 系列为例
yum install -y java-11-openjdk java-11-openjdk-devel

# 创建 kafka 用户及目录
useradd -m -s /bin/bash kafka
mkdir -p /opt/kafka /data/kafka-logs /data/kafka-meta
chown -R kafka:kafka /opt/kafka /data/kafka-logs /data/kafka-meta

3.2 下载并解压 Kafka 4.1.1

前往 Kafka 官方下载页,找到 4.1.1 对应的 Scala 2.13 二进制包,链接一般形如:

cd /opt

# 示例命令,具体下载 URL 请以官网为准
curl -O https://downloads.apache.org/kafka/4.1.1/kafka_2.13-4.1.1.tgz

tar -xzf kafka_2.13-4.1.1.tgz
ln -s kafka_2.13-4.1.1 kafka

chown -R kafka:kafka /opt/kafka_2.13-4.1.1 /opt/kafka

之后所有操作默认在 kafka 用户下进行:

su - kafka
cd /opt/kafka

3.3 编写 KRaft 配置:config/kraft/server.properties

备份原有配置:

cp config/kraft/server.properties config/kraft/server.properties.bak

编辑 config/kraft/server.properties

######################### 基本标识 #########################
# 当前节点 ID,整型且集群唯一
node.id=1

# 单进程既是 broker 又是 controller
process.roles=broker,controller

# Controller 投票者(单节点)
controller.quorum.voters=1@localhost:9093

######################### 监听配置 #########################
# 监听地址:
# - PLAINTEXT:集群内部 + 客户端访问
# - CONTROLLER:KRaft controller 通讯
listeners=PLAINTEXT://0.0.0.0:9092,CONTROLLER://0.0.0.0:9093
listener.security.protocol.map=PLAINTEXT:PLAINTEXT,CONTROLLER:PLAINTEXT

# broker 间通信 listener 名称
inter.broker.listener.name=PLAINTEXT

######################### 日志目录 #########################
# Topic 数据日志目录
log.dirs=/data/kafka-logs

# KRaft 元数据日志目录
metadata.log.dir=/data/kafka-meta

######################### Topic 默认配置 #########################
# 默认分区数
num.partitions=3

# 日志保留时间(小时)
log.retention.hours=168

# 单个 segment 大小:1GB
log.segment.bytes=1073741824

# 内部主题副本数(单机环境只能设为 1)
offsets.topic.replication.factor=1
transaction.state.log.replication.factor=1
transaction.state.log.min.isr=1

######################### 其他 #########################
# 生产环境建议打开的参数可以按需追加:
# auto.create.topics.enable=false
# unclean.leader.election.enable=false

多节点时需要为每个节点设置不同的 node.id,并在 controller.quorum.voters 中列出所有 controller,如:
controller.quorum.voters=1@kafka1:9093,2@kafka2:9093,3@kafka3:9093

3.4 初始化 KRaft 元数据存储

4.x 的 KRaft 模式必须先用 kafka-storage.sh 进行格式化,否则 broker 无法启动。

仍然在 kafka 用户下:

3.4.1 生成集群 ID
cd /opt/kafka
bin/kafka-storage.sh random-uuid
# 比如输出:fRbs-vkR9Uevh5Cwlwk
3.4.2 格式化存储
bin/kafka-storage.sh format   -t fRbs-vkR9Uevh5Cwlwk   -c config/kraft/server.properties

如果修改过 log.dirsmetadata.log.dir,重新格式化前记得清空对应目录。

3.5 启动 Kafka(手工 & systemd)

3.5.1 手工启动(测试用)

前台启动(便于看日志):

bin/kafka-server-start.sh config/kraft/server.properties

后台启动:

bin/kafka-server-start.sh -daemon config/kraft/server.properties

查看日志:

tail -f /opt/kafka/logs/server.log
3.5.2 使用 systemd 管理 Kafka

切回 root 用户,创建 /etc/systemd/system/kafka.service

[Unit]
Description=Apache Kafka 4.1.1 Server (KRaft)
After=network.target

[Service]
User=kafka
Group=kafka
Type=simple
Environment="JAVA_HOME=/usr/lib/jvm/java-11-openjdk"
ExecStart=/opt/kafka/bin/kafka-server-start.sh /opt/kafka/config/kraft/server.properties
ExecStop=/opt/kafka/bin/kafka-server-stop.sh
Restart=on-failure
RestartSec=5

[Install]
WantedBy=multi-user.target

加载并设置自启动:

systemctl daemon-reload
systemctl enable kafka
systemctl start kafka
systemctl status kafka

3.6 本地命令行验证

以下命令同样在 kafka 用户下执行。

3.6.1 创建 Topic
cd /opt/kafka

bin/kafka-topics.sh --create   --topic demo-topic   --bootstrap-server localhost:9092   --partitions 3   --replication-factor 1
3.6.2 列出 Topic
bin/kafka-topics.sh --list --bootstrap-server localhost:9092
3.6.3 生产 & 消费
# 生产者
bin/kafka-console-producer.sh   --topic demo-topic   --bootstrap-server localhost:9092

# 消费者
bin/kafka-console-consumer.sh   --topic demo-topic   --from-beginning   --bootstrap-server localhost:9092

4. 生产环境部署建议(简要)

这里只给出一些通用的建议,细节可以根据公司规范和官方文档再细化。

  1. 节点规模

    • 至少 3 个 broker + 3 个 controller(可以共进程,也可以分离)。
    • 关键业务建议独立 controller 集群,避免业务负载影响元数据选举。
  2. 磁盘与路径规划

    • 建议使用 SSD。
    • log.dirs 配置为多个挂载点,分散 IO 压力,如:
      log.dirs=/data/kafka-logs1,/data/kafka-logs2,...
  3. Topic 副本与 ISR

    • 重要 Topic:replication.factor=3min.insync.replicas>=2
    • 禁止 unclean.leader.election.enable=true,避免数据丢失。
  4. 监控与告警

    • 建议接入 Prometheus + Grafana 或其他监控系统,重点关注:
      • Under-replicated partitions
      • ISR 变化
      • 磁盘使用率、日志保留时间
      • Controller 选举频率
      • 请求延迟(p95 / p99)
  5. 安全

    • 生产环境建议启用 TLS + SASL(如 SCRAM / OAuth / JWT),并关闭明文端口。
    • 对外暴露时,注意 advertised.listeners 使用内网域名 + LB。

5. 常见问题排查思路

  1. 客户端连不上 Kafka

    • 检查 advertised.listeners / KAFKA_ADVERTISED_LISTENERS 是否使用了正确的 IP / 域名。
    • 在客户端所在机器上 telnet host 9092nc -vz host 9092
  2. Broker 启动报错:未初始化元数据(KRaft)

    • 是否执行过 kafka-storage.sh format
    • 是否修改过 log.dirs / metadata.log.dir 却没重新 format。
  3. Topic 创建报错:副本数过大

    • 单机时 replication.factor 只能为 1,否则会报 “not enough replicas”。
  4. 消费不到旧数据

    • 是否忘记加 --from-beginning
    • 是否设置了消费组 group.id,且该组已经消费过。

6. 小结

本文以 Kafka 4.1.1 为例,从零搭建了两套完整环境:

  1. 使用官方 Docker 镜像 apache/kafka:4.1.1容器化部署(适合本地开发与轻量级场景)。
  2. 使用 kafka_2.13-4.1.1.tgz二进制部署(适合结合现有运维体系的传统或生产环境)。

如果你习惯用容器平台(Kubernetes、OpenShift 等),可以在此基础上进一步封装 Helm Chart 或 Operator;如果你是传统运维,则可以继续补充监控、日志、备份等内容,将本文作为公司内部《Kafka 4.1 部署规范》的雏形。

Logo

汇聚全球AI编程工具,助力开发者即刻编程。

更多推荐