Kafka KRaft 模式部署专业方案(下)
#作者:张桐瑞
文章目录
- 6. 详细部署步骤(KRaft 模式)
-
- 6.1 生成集群 ID
- 6.2 控制器节点配置与格式化
-
- 6.2.1 控制器配置文件(以 controller-01 为例)
- 6.2.2 为多控制器生成单独目录 ID(可选)
- 6.2.3 格式化控制器存储
- 6.2.4 启动控制器服务(systemd 示例)
- 6.3 Broker 节点配置与格式化
-
- 6.3.1 Broker 配置文件示例
- 6.3.2 格式化 Broker 存储
- 6.3.3 启动 Broker 服务(systemd 示例)
- 7. 集群状态验证与基础运维命令
-
- 7.1 验证控制器 Quorum 状态
- 7.2 检查 KRaft 版本与 Quorum 模式
- 8. 配置参数要点与模板
-
- 8.1 角色与标识相关参数
- 8.2 高可用相关参数建议
- 9. 动态扩容控制器与 Broker
-
- 9.1 动态增加控制器(KRaft 动态 Quorum)
- 9.2 扩容 Broker
- 10. 安全加固建议(概要)
-
- 10.1 传输加密(TLS)
- 10.2 认证与授权
- 11. 监控与故障排查要点
-
- 11.1 监控推荐
- 11.2 典型问题排查思路
- 12. 从 ZooKeeper 迁移到 KRaft(高层方案)
- 13. 最佳实践清单(可作为投产前检查表)
6. 详细部署步骤(KRaft 模式)
6.1 生成集群 ID
在任一节点执行一次,并记录:
sudo -u kafka /opt/kafka/bin/kafka-storage.sh random-uuid
# 输出形如:vCj5WbkrQ8KDXzzq5gJm3Q
# 该值即为 CLUSTER_ID,在所有节点统一使用
6.2 控制器节点配置与格式化
6.2.1 控制器配置文件(以 controller-01 为例)
/etc/kafka/controller.properties:
# 角色
process.roles=controller
node.id=1
# 控制器监听
listeners=CONTROLLER://0.0.0.0:9093
controller.listener.names=CONTROLLER
# 动态 Quorum 控制器集合
controller.quorum.bootstrap.servers=controller-01.example.com:9093,controller-02.example.com:9093,controller-03.example.com:9093
# 元数据存储目录
metadata.log.dir=/var/lib/kafka/controller
# 基本线程与网络
num.network.threads=3
num.io.threads=8
socket.send.buffer.bytes=1024000
socket.receive.buffer.bytes=1024000
socket.request.max.bytes=104857500
# 安全映射(如使用明文)
listener.security.protocol.map=CONTROLLER:PLAINTEXT
注:node.id 在整个集群内必须唯一。可以为控制器分配小整数(1,2,3),Broker 使用更大的 ID。
6.2.2 为多控制器生成单独目录 ID(可选)
官方文档中推荐在多控制器初始化时,为每个控制器生成唯一目录 UUID,用于动态 Quorum 的初始控制器信息。
示例(在某节点上生成,然后分配给各控制器):
CONTROLLER_0_UUID=KaTeX parse error: Double subscript at position 59: …d) CONTROLLER_1_̲UUID=(/opt/kafka/bin/kafka-storage.sh random-uuid)
CONTROLLER_2_UUID=$(/opt/kafka/bin/kafka-storage.sh random-uuid)
6.2.3 格式化控制器存储
在每台控制器上执行(保持 –initial-controllers 完全一致):
sudo -u kafka /opt/kafka/bin/kafka-storage.sh format \
--cluster-id <CLUSTER_ID> \
--initial-controllers "0@controller-01.example.com:9093:${CONTROLLER_0_UUID},1@controller-02.example.com:9093:${CONTROLLER_1_UUID},2@controller-03.example.com:9093:${CONTROLLER_2_UUID}" \
--config /etc/kafka/controller.properties
- 会在 metadata.log.dir 下生成 meta.properties 和元数据日志。
- 只在首次集群初始化执行,后续新增控制器使用 --no-initial-controllers。
6.2.4 启动控制器服务(systemd 示例)
/etc/systemd/system/kafka-controller.service:
[Unit]
Description=Apache Kafka Controller
After=network.target
[Service]
User=kafka
Group=kafka
Environment="KAFKA_HEAP_OPTS=-Xmx4g -Xms4g"
ExecStart=/opt/kafka/bin/kafka-server-start.sh /etc/kafka/controller.properties
Restart=always
RestartSec=10
[Install]
WantedBy=multi-user.target
加载并启动:
sudo systemctl daemon-reload
sudo systemctl enable kafka-controller
sudo systemctl start kafka-controller
6.3 Broker 节点配置与格式化
6.3.1 Broker 配置文件示例
/etc/kafka/server.properties:
# 角色
process.roles=broker
node.id=4
# 客户端监听
listeners=PLAINTEXT://0.0.0.0:9092
advertised.listeners=PLAINTEXT://broker-01.example.com:9092
inter.broker.listener.name=PLAINTEXT
listener.security.protocol.map=PLAINTEXT:PLAINTEXT,CONTROLLER:PLAINTEXT
# 控制器连接(指向控制器集群)
controller.quorum.bootstrap.servers=controller-01.example.com:9093,controller-02.example.com:9093,controller-03.example.com:9093
controller.listener.names=CONTROLLER
# 日志存储
log.dirs=/var/lib/kafka/broker
# Topic 默认参数
num.partitions=3
default.replication.factor=3
min.insync.replicas=2
# 性能调优
num.network.threads=5
num.io.threads=8
num.replica.fetchers=4
replica.socket.timeout.ms=30000
socket.send.buffer.bytes=1024000
socket.receive.buffer.bytes=1024000
socket.request.max.bytes=104857500
# 数据保留策略(按需调整)
log.segment.bytes=1073741824
log.retention.hours=168
log.retention.check.interval.ms=300000
所有 Broker 的 controller.quorum.bootstrap.servers 必须完全一致,并指向生产中的控制器地址。
6.3.2 格式化 Broker 存储
注意:Broker 加入已经初始化好的 KRaft 集群时,一律使用 –no-initial-controllers。
sudo -u kafka /opt/kafka/bin/kafka-storage.sh format
–cluster-id <CLUSTER_ID>
–config /etc/kafka/server.properties
–no-initial-controllers
6.3.3 启动 Broker 服务(systemd 示例)
/etc/systemd/system/kafka-broker.service:
[Unit]
Description=Apache Kafka Broker
After=network.target
[Service]
User=kafka
Group=kafka
Environment="KAFKA_HEAP_OPTS=-Xmx8g -Xms8g"
ExecStart=/opt/kafka/bin/kafka-server-start.sh /etc/kafka/server.properties
Restart=always
RestartSec=10
[Install]
WantedBy=multi-user.target
sudo systemctl daemon-reload
sudo systemctl enable kafka-broker
sudo systemctl start kafka-broker
7. 集群状态验证与基础运维命令
7.1 验证控制器 Quorum 状态
/opt/kafka/bin/kafka-metadata-quorum.sh \
--bootstrap-server broker-01.example.com:9092 \
describe --status
可看到:
- ClusterId
- LeaderId(当前控制器 leader)
- CurrentVoters(当前控制器成员)
- HighWatermark 等关键信息。
7.2 检查 KRaft 版本与 Quorum 模式
/opt/kafka/bin/kafka-features.sh \
--bootstrap-server broker-01.example.com:9092 \
describe
关注 Feature: kraft.version 行:
- 若 FinalizedVersionLevel=0 或不存在,通常为 静态 Quorum
- 若 FinalizedVersionLevel>=1,为 动态 Quorum
8. 配置参数要点与模板
8.1 角色与标识相关参数
| 参数名 | 说明 | 典型设置示例 |
|---|---|---|
| process.roles | 进程角色:broker / controller / both | 控制器:controller |
| node.id | 集群内唯一整型 ID | 控制器 1、2、3;Broker 从 4 开始 |
| controller.quorum.bootstrap.servers | 动态 Quorum 控制器列表 | controller-01:9093,… |
| controller.listener.names | 指明用作控制器的 listener 名称 | CONTROLLER |
| metadata.log.dir | 控制器元数据日志目录 | /var/lib/kafka/controller |
| log.dirs | Broker 数据目录 | /var/lib/kafka/broker |
8.2 高可用相关参数建议
- default.replication.factor=3
- min.insync.replicas=2
- unclean.leader.election.enable=false(避免脏读写)
- auto.leader.rebalance.enable=true(适度启用)
9. 动态扩容控制器与 Broker
9.1 动态增加控制器(KRaft 动态 Quorum)
当使用动态 Quorum 时,可通过命令增加 / 删除控制器成员。
增加控制器(示意):
- 按前述方式准备一个新控制器配置、格式化(使用 –no-initial-controllers)。
- 通过 kafka-metadata-quorum.sh 命令把新控制器加入 Quorum。
根据官方示例,命令形式类似:
/opt/kafka/bin/kafka-metadata-quorum.sh \
--bootstrap-server broker-01.example.com:9092 \
add-controller \
--controller-id <id> \
--controller-directory-id <directory-uuid>
具体参数需参考当前 Kafka 版本文档,保持与 metadata.log.dir 对应的目录 ID 一致。
9.2 扩容 Broker
扩容 Broker 相对简单,只需:
- 新节点配置 process.roles=broker、唯一的 node.id。
- kafka-storage.sh format –cluster-id <CLUSTER_ID> –no-initial-controllers
- 启动 Broker 后,基于 Cruise Control 或手动方式进行数据重分布。
10. 安全加固建议(概要)
10.1 传输加密(TLS)
- 为控制器和 Broker 分别启用 TLS:
- 控制器端:listener.security.protocol.map=CONTROLLER:SSL
- Broker 客户端端口:PLAINTEXT:SSL 或 SASL_SSL
- 每个节点使用独立证书,统一 CA 签发。
10.2 认证与授权
- 启用 SASL(如 SASL/SCRAM)进行客户端认证。
- 使用 Kafka ACL 做细粒度权限控制。
- 在 KRaft 下,ACL 和所有安全元数据同样由控制器 Quorum 管理。
11. 监控与故障排查要点
11.1 监控推荐
- 控制器:
- 选举次数、选举耗时
- 元数据日志大小与同步延迟
- Broker:
- 吞吐量、请求延迟、分区 Leader 负载
- 副本同步延迟(Follower Lag)
- 集群层:
- kafka-metadata-quorum.sh … describe –status 输出的关键指标
11.2 典型问题排查思路
| 现象 | 排查方向 |
|---|---|
| 部分 Broker 无法启动,报 ClusterId 不匹配 | 检查 meta.properties 中的 cluster.id 是否与全局一致 |
| 报错找不到控制器或连接被拒绝 | 检查 controller.quorum.bootstrap.servers 地址和端口是否正确 |
| 集群频繁 Leader 选举 | 检查控制器节点稳定性(CPU/内存/网络抖动),查看控制器日志 |
| 部分 Topic 变为 Leader not available | 检查控制器 leader 状态和 Broker 存活情况,查看 quorum describe |
12. 从 ZooKeeper 迁移到 KRaft(高层方案)
详细迁移步骤需与具体 Kafka 版本文档对齐,这里给出总体思路框架 。
- 升级至支持迁移的 Kafka 版本(如官方给出的 bridge 版本)。
- 在现有 ZooKeeper 模式集群中,使用官方迁移工具导出元数据:
类似 kafka-migrate-zk-to-kraft.sh export-zk。 - 部署新 KRaft 控制器集群,格式化使用统一 cluster-id。
- 导入 ZooKeeper 元数据至 KRaft:
类似 kafka-migrate-zk-to-kraft.sh import-kraft。 - 分批将 Broker 切换为 KRaft 模式,观察业务稳定性。
- 迁移完成并验证后,逐步停用 ZooKeeper。
迁移必须在 受控维护窗口 内进行,并有完整回滚方案。
13. 最佳实践清单(可作为投产前检查表)
部署前:
- 所有节点时间同步(NTP)
- 明确的主机命名与 DNS 解析
- cluster.id 在所有节点保持一致
- 控制器与 Broker 角色划分清晰(建议分离)
配置检查:
- 所有控制器 controller.quorum.bootstrap.servers 完全一致
- 所有 Broker controller.quorum.bootstrap.servers 指向正确控制器列表
- 各节点 node.id 唯一
- metadata.log.dir 与 log.dirs 不冲突,权限归 kafka 用户
- 默认复制因子、分区数、min.insync.replicas 符合业务高可用要求
上线与监控:
- 使用 kafka-metadata-quorum.sh … describe –status 验证 Quorum 正常
- 配置日志与监控系统(Prometheus + Grafana / Commercial)
压测读写性能并验证故障场景(单节点、双节点故障)