集群参数配置
Broker 端参数
- log.dirs:指定了 Broker 需要使用的若干个文件目录路径。这个参数没有默认值,必须亲自指定。
- log.dir:注意这是 dir,结尾没有 s,说明它只能表示单个路径,它是补充上一个参数。
在线上生产环境中一定要为log.dirs配置多个路径,保证这些目录挂载到不同的物理磁盘上。这样做有两个好处:
- 提升读写性能:比起单块磁盘,多块物理磁盘同时读写数据有更高的吞吐量。
- 能够实现故障转移:即 Failover。
ZooKeeper 相关的设置
- zookeeper.connect
Broker 连接
- listeners:监听器,告诉外部连接者要通过什么协议访问指定主机名和端口开放的 Kafka 服务。
- advertised.listeners:这组监听器是 Broker 用于对外发布。
- listener.security.protocol.map:当自定义协议名称时,底层使用了哪种安全协议。
注意:主机名这个设置最好全部使用主机名,而非IP 地址,即 Broker 端和 Client 端应用配置中全部填写主机名。
Topic 管理
- auto.create.topics.enable:是否允许自动创建Topic。建议最好设置成 false,即不允许自动创建 Topic。每个部门被分配的 Topic 应该由运维严格把控,决不能允许自行创建任何 Topic。
- unclean.leader.election.enable:是否允许 Unclean Leader 选举。即副本是否都有资格竞争 Leader。把它设置成 false,避免落后进度太多的副本进行选举。
- auto.leader.rebalance.enable:是否允许定期进行 Leader 选举。换 Leader 本质上没有任何性能收益,设置成 false。
数据留存
-
log.retention.{hour minutes ms}:控制一条消息数据被保存多长时间。从优先级上来说 ms 设置最高、minutes 次之、hour 最低。 - log.retention.bytes:指定 Broker 为消息保存的总磁盘容量大小。
- message.max.bytes:控制 Broker 能够接收的最大消息大小。
Topic 级别参数
注:Topic 级别参数会覆盖全局 Broker 参数的值,而每个 Topic 都能设置自己的参数值。
- retention.ms:该 Topic 消息被保存的时长。默认是 7 天,即该 Topic 只保存最近 7 天的消息。一旦设置了这个值,它会覆盖掉 Broker 端的全局参数值。
- retention.bytes:为该 Topic 预留多大的磁盘空间。和全局参数作用相似,这个值通常在多租户的 Kafka 集群中会有用武之地。当前默认值是 -1,表示可以无限使用磁盘空间。
- max.message.bytes:Kafka Broker 能够正常接收该 Topic 的最大消息大小。
JVM 参数
Kafka 服务器端代码是用 Scala 语言编写的,但终归还是编译成 Class 文件在 JVM 上运行,因此 JVM 参数设置对于 Kafka 集群的重要性不言而喻。
- Java 版本至少使用Java 8
- JVM 堆大小设置成 6GB
设置下面这两个环境变量即可:
- KAFKA_HEAP_OPTS:指定堆大小。
- KAFKA_JVM_PERFORMANCE_OPTS:指定 GC 参数。
操作系统参数
- 文件描述符限制:ulimit -n。文件描述符系统资源并不像想象的那样昂贵,不用太担心调大此值会有什么不利的影响。通常情况下将它设置成一个超大的值是合理的做法,比如 ulimit -n 1000000。
- 文件系统类型:XFS 的性能要强于 ext4。
- Swappiness:配置成一个接近 0 但不为 0 的值,比如 1。网上很多文章都提到设置其为 0,将 swap 完全禁掉以防止 Kafka 进程使用 swap 空间。但还是不要设置成 0 比较好,可以设置成一个较小的值。为什么呢?因为一旦设置成 0,当物理内存耗尽时,操作系统会触发 OOM killer 这个组件,它会随机挑选一个进程然后 kill 掉,即根本不给用户任何的预警。但如果设置成一个比较小的值,当开始使用 swap 空间时,至少能够观测到 Broker 性能开始出现急剧下降,从而有进一步调优和诊断问题的时间。
- 提交时间(Flush 落盘时间):向 Kafka 发送数据并不是真要等数据被写入磁盘才会认为成功,而是只要数据被写入到操作系统的页缓存(Page Cache)上就可以了,随后操作系统根据 LRU 算法会定期将页缓存上的“脏”数据落盘到物理磁盘上。这个定期就是由提交时间来确定的,默认是 5 秒。一般情况下我们会认为这个时间太频繁了,可以适当地增加提交间隔来降低物理磁盘的写操作。