# 修改Kafka分区平衡
分区平衡是指将分区的副本重新分配到不同的代理上，解决代理负载不均衡问题。
需要进行分区平衡的场景如下：
- 实例扩容代理个数后，新创建的Topic才会分布在新代理上，原有Topic还分布在原有代理上，造成分区分布不均衡。通过修改分区平衡，将原有Topic分区的副本迁移到新代理上。
- 将高负载代理上的Leader分区切换为Follower。
- 在修改分区平衡过程中，可以配置增加/减少Topic的副本数。
#### 操作视频
本视频演示修改Kafka实例分区平衡的操作。
因产品功能演进，操作界面可能存在差异，相关视频仅供参考，具体以实际环境为准。
<video controls="controls" preload="none" id="object106975193118" class="idp-external-video" src="https://res-video.hc-cdn.com/cloudbu-site/china/zh-cn/support/kafka-video/ReassigningPartitions.mp4" title="修改分区平衡" poster="https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000002406374709.jpg" height="335.0000" width="600.0000"></video>
#### 约束与限制
- 单机实例不支持修改分区平衡。
- 分区平衡任务启动后，无法修改Topic的分区数。
- 分区平衡任务启动后，无法手动停止任务，需要等到任务完成。
- 已设置了一个定时分区平衡任务，在此任务未执行前，无法对本实例内的任何Topic执行其他分区平衡任务。
- 若Topic创建时未开启同步复制功能，且后续从未手动修改过该状态，那么修改分区平衡时，需确保新设置的副本数大于等于"[min.insync.replicas](https://support.huaweicloud.com/usermanual-kafka/kafka-ug-0007.html)"参数值，否则会导致修改分区平衡失败。
 
#### 操作影响
- 对数据量大的Topic进行分区平衡会占用大量的网络和存储带宽，业务可能会出现请求超时或者时延增大，建议在业务低峰期时操作。对Topic进行分区平衡前，根据Kafka实例规格对比当前实例负载情况，评估是否可以进行分区平衡，建议预留足够的带宽进行分区平衡，CPU使用率在90%以上时，不建议进行分区平衡。Topic的数据量和CPU使用率可以通过监控页面的"数据容量"和"CPU使用率"查看，具体步骤请参考[查看Kafka监控数据](https://support.huaweicloud.com/usermanual-kafka/kafka-ug-190605001.html)。
- 带宽限制是指设定Topic进行副本同步的带宽上限，确保不会对该实例上的其他Topic造成流量冲击。但需要注意，带宽限制不会区分是正常的生产消息造成的副本同步还是分区平衡造成的副本同步，如果带宽限制设定过小，可能会影响正常的生产消息，且可能会造成分区平衡一直无法结束。如果分区平衡一直无法结束，请联系客服处理。
- 分区平衡任务启动后，不能删除正在进行分区平衡的Topic，否则会导致分区平衡任务无法结束。
- 分区平衡后Topic的metadata会改变，如果生产者不支持重试机制，会有少量的请求失败，导致部分消息生产失败。
- 数据量大的Topic进行分区平衡的时间会比较长。Topic的数据量可以通过监控页面的"数据容量"查看，具体步骤请参考[查看Kafka监控数据](https://support.huaweicloud.com/usermanual-kafka/kafka-ug-190605001.html)。在不影响业务的前提下，建议适当[调小Topic老化时间](https://support.huaweicloud.com/usermanual-kafka/kafka-ug-200506001.html)并等待消息老化，减少迁移数据，加快迁移速度。分区平衡任务结束后可重新调整为初始值。
 
#### 前提条件
确保分区平衡的目标Broker磁盘容量充足，在[磁盘存储统计](https://support.huaweicloud.com/usermanual-kafka/kafka-ug-0004.html)中查看每个Broker的可用磁盘容量。如果目标Broker磁盘剩余容量接近分区平衡迁移到该Broker上的数据量，为了给目标Broker上的消息生产预留存储空间，应先进行[磁盘扩容](https://support.huaweicloud.com/usermanual-kafka/kafka-ug-181221001.html)，再进行分区平衡。
#### 修改Kafka分区平衡
Kafka控制台提供两种分区平衡的方法：
- 自动平衡：支持批量修改Topic的分区平衡。
- 手动平衡：每次只能修改一个Topic的分区平衡。
 
- [自动平衡]
  1. 登录[Kafka控制台](https://console.huaweicloud.com/dms/?engine=kafka&locale=zh-cn#/queue/manager/newKafkaList)。
  
  2. 在管理控制台左上角单击![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0143929918.png)，选择Kafka实例所在的区域。
  
  3. 在管理控制台左上角单击![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000001143589128.png)，选择"应用服务 \> 分布式消息服务 Kafka"，进入Kafka实例列表页面。
  
  4. 单击Kafka实例的名称，进入实例详情页面。
  
  5. 在左侧导航栏单击"实例管理 \> Topic管理"，进入Topic列表页面。
  
  6. 通过以下任意一种方法，修改分区平衡。 
     - 勾选Topic名称左侧的方框，可选一个或多个，单击信息栏左上侧的"一键平衡 \> 自动平衡"。
     
     - 在待修改分区平衡的Topic所在行，单击"更多 \> 一键平衡 \> 自动平衡"。
     
     
     
     
  
  7. 设置自动平衡参数。 
     表1自动平衡参数说明 
     | 参数名称    | 说明                                                                                                                                                                                                                                                                                                                                                                                       |
     |:---|:---|
     | Broker名称 | 勾选目标Broker的名称，Topic分区的副本即将迁移至目标Broker上。                                                                                                                                                                                                                                                                                                                                                    |
     | 副本数       | 输入Topic需要自动平衡的副本数，副本数须小于等于Broker的数量。                                                                                                                                                                                                                                                                                                                                                        |
     | 带宽限制     | 输入带宽大小，默认值为"100MB/s"，取值范围：1\~300MB/s，或-1。输入"-1"时表示不限制带宽。 如果实例负载较低（例如实例规格为300MB/s，当前实例负载为30MB/s），建议不设置带宽限制。如果需要设置带宽限制，建议该参数值不小于待分区平衡Topic的总生产带宽 \* 待分区平衡Topic的最大副本数。 带宽限制值的估算方法，请参考[带宽限制值估算方法]。 带宽设置完成后，在对话框底部的确认下发此带宽处，单击"一键输入"或手动输入"YES"，完成带宽下发确认。 |
     | 执行时间     | 选择分区平衡任务执行的时间。 - 立即执行：表示立即执行分区平衡任务。  - 定时执行：表示在指定的时间执行分区平衡任务。                                                                                                                                                            |
        
     图1设置自动平衡参数   
     ![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000002539840219.png "点击放大")
     
     
  
  8. （可选）单击"一键测算"，在"预估耗时"中，显示执行自动平衡大概需要的时间。 
     一键测算功能对Kafka实例性能没有影响。
     
     
  
  9. 单击"确定"。 
     定时任务和非定时任务查看分区平衡是否完成的方法不同，具体如下：
     表2查看分区平衡结果 
     | 任务类型 | 分区平衡结果                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
     |:---|:---|
     | 非定时任务 | 在Topic列表页面左上方单击"查看变更任务"，进入"后台任务管理 \> 即时任务"页面，当任务的"状态"为"成功"时，表示分区平衡完成。                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                   |
     | 定时任务 | 1. 系统自动跳转到"后台任务管理 \> 定时任务"页面，此页面的状态仅表示定时任务是否开始执行，并非表示任务是否执行成功。 - 当"状态"为"待执行"时，表示定时分区平衡任务未执行。  - 当"状态"为"成功"时，表示定时分区平衡任务开始执行。  - 当"状态"为"取消"时，表示已取消定时分区平衡任务。    2. 单击"即时任务"，进入"即时任务"页签，查看任务的状态。当任务的"状态"为"成功"时，表示分区平衡完成。   |
        
     图2后台任务管理页面   
     ![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000002473955213.png "点击放大")
     ![](https://support.huaweicloud.com/usermanual-kafka/public_sys-resources/note_3.0-zh-cn.png)
     - 分区平衡任务启动后，不能删除正在进行分区平衡的Topic，否则会导致分区平衡任务无法结束。
     
     - 分区平衡任务启动后，无法修改Topic的分区数。
     
     - 分区平衡任务启动后，无法手动停止任务，需要等到任务完成。
     
     - 已设置了一个定时分区平衡任务，在此任务未执行前，无法对本实例内的任何Topic执行其他分区平衡任务。
      
     
     
   
- [手动平衡]
  1. 登录[Kafka控制台](https://console.huaweicloud.com/dms/?engine=kafka&locale=zh-cn#/queue/manager/newKafkaList)。
  
  2. 在管理控制台左上角单击![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0143929918.png)，选择Kafka实例所在的区域。
  
  3. 单击Kafka实例的名称，进入实例详情页面。
  
  4. 在左侧导航栏单击"实例管理 \> Topic管理"，进入Topic列表页面。
  
  5. 通过以下任意一种方法，修改分区平衡。 
     - 勾选Topic名称左侧的方框，手动平衡每次只能勾选一个Topic，单击信息栏左上侧的"一键平衡 \> 手动平衡"。
     
     - 在待修改分区平衡的Topic所在行，单击"更多 \> 一键平衡 \> 手动平衡"。
     
     
     
     
  
  6. 设置手动平衡参数。 
     - 在"手动平衡"对话框右上角，单击"减少副本"/"添加副本"，为Topic的每个分区减少/增加副本数。
     
     - 在待修改分区平衡的副本名称下，单击Broker名称或![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000001453201733.png)，选择目标Broker的名称，副本即将迁移至目标Broker上。同一分区下的不同副本需要分配在不同的Broker上。
     
     - 在"带宽限制"中，输入带宽大小，默认值为"100MB/s"，取值范围：1\~300MB/s，或-1。输入"-1"时表示不限制带宽。 如果实例负载较低（例如实例规格为300MB/s，当前实例负载为30MB/s），建议不设置带宽限制。如果需要设置带宽限制，建议该参数值不小于待分区平衡Topic的总生产带宽 \* 待分区平衡Topic的最大副本数。带宽限制值的估算方法，请参考[带宽限制值估算方法]。
       带宽设置完成后，在对话框底部的确认下发此带宽处，单击"一键输入"或手动输入"YES"，完成带宽下发确认。
       
     
     - 在"执行时间"中，选择分区平衡任务执行的时间。"立即执行"表示立即执行分区平衡任务。"定时执行"表示在指定的时间执行分区平衡任务。
     
     
     图3设置手动平衡参数   
     ![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000002508161166.png "点击放大")
     
     
  
  7. （可选）单击"一键测算"，在"预估耗时"中，显示执行手动平衡大概需要的时间。 
     一键测算功能对Kafka实例性能没有影响。
     
     
  
  8. 单击"确定"。 
     定时任务和非定时任务查看分区平衡是否完成的方法不同，具体如下：
     表3查看分区平衡结果 
     | 任务类型 | 分区平衡结果                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
     |:---|:---|
     | 非定时任务 | 在Topic列表页面左上方单击"查看变更任务"，进入"后台任务管理 \> 即时任务"页面，当任务的"状态"为"成功"时，表示分区平衡完成。                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                             |
     | 定时任务 | 1. 系统自动跳转到"后台任务管理 \> 定时任务"页面，此页面的状态仅表示定时任务是否开始执行，并非表示任务是否执行成功。 - 当"状态"为"待执行"时，表示定时分区平衡任务未执行。  - 当"状态"为"成功"时，表示定时分区平衡任务开始执行。  - 当"状态"为"取消"时，表示已取消定时分区平衡任务。    2. 单击"即时任务"，进入"即时任务"页签，查看任务的状态。当任务的"状态"为"成功"时，表示分区平衡完成。   |
        
     图4后台任务管理页面   
     ![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000002473955213.png "点击放大")
     ![](https://support.huaweicloud.com/usermanual-kafka/public_sys-resources/note_3.0-zh-cn.png)
     - 分区平衡任务启动后，不能删除正在进行分区平衡的Topic，否则会导致分区平衡任务无法结束。
     
     - 分区平衡任务启动后，无法修改Topic的分区数。
     
     - 分区平衡任务启动后，无法手动停止任务，需要等到任务完成。
     
     - 已设置了一个定时分区平衡任务，在此任务未执行前，无法对本实例内的任何Topic执行其他分区平衡任务。
      
     
     
   
#### 修改定时分区平衡任务
1. 在"实例管理 \> 后台任务管理"页面的"定时任务"页签中，单击页面左上角下拉框，选择时间段，在搜索对话框中输入待修改定时分区平衡任务的Topic名称，按"Enter"，实现快速查找定时分区平衡任务。 
   图5查找定时分区平衡任务   
   ![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000002440464352.png "点击放大")
   
   
2. 在待修改的定时分区平衡任务后，单击"修改"。
3. 在弹出的"修改定时任务"对话框中，您可以修改定时分区平衡任务的时间，还可以取消定时分区平衡任务，具体操作如下。 
   - 修改定时分区平衡任务的时间：修改时间，单击"确定"。
   
   - 取消定时分区平衡任务：选择"取消"，如[图6]所示，单击"确定"。
     图6取消定时分区平衡任务   
     ![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000001930266517.png "点击放大") 
   
   
   
   
 
 #### 带宽限制值估算方法
带宽限制值受分区平衡任务执行时间、分区副本Leader/Follower分布情况以及消息生产速率等因素影响，具体分析如下。
- 带宽限制值作用范围为整个Broker，对该Broker内所有副本同步的分区进行带宽限流。
- 带宽限制会将分区平衡后新增的副本视为Follower副本限流，分区平衡前的Leader副本视为Leader副本限流，Leader副本的限流和Follower副本限流分开计算。
- 带宽限制不会区分是正常的生产消息造成的副本同步还是分区平衡造成的副本同步，因此两者的流量都会被限流统计。
假设分区平衡任务需要在200s内完成，每个副本的数据量为100MB，在以下几种场景中，估算带宽限制值。
**场景一：** **Topic1有2分区2副本，Topic2有1分区1副本，** **所有Leader副本在同一个Broker上** **，如[表4]所示，** **Topic1和Topic2分别需要新增1个副本，如** [表5]**所示**。
 表4分区平衡前Topic分区的副本分布 
| Topic名称 | 分区名称 | Leader副本所在Broker | Follower副本所在Broker |
|:---|:---|:---|:---|
| Topic1 | 0    | 0                 | 0，1                  |
| Topic1 | 1   | 0                | 0，2                |
| Topic2  | 0    | 0                | 0                 |
   
 表5分区平衡后Topic分区的副本分布 
| Topic名称 | 分区名称  | Leader副本所在Broker | Follower副本所在Broker |
|:---|:---|:---|:---|
| Topic1   | 0  | 0                 | 0，1，2             |
| Topic1    | 1 | 0                | 0，1，2           |
| Topic2     | 0    | 0                | 0，2                |
   
图7场景一分区平衡图   
![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000001403219302.png "点击放大")
如[图7]所示，有3个副本需要从Broker 0拉取数据，Broker 0中每个副本的数据量为100MB，Broker 0中只有Leader副本，Broker 1和Broker 2中只有Follower副本，由此得出以下数据：
- Broker 0在200s内完成分区平衡所需的带宽限制值=（100+100+100）/200=1.5MB/s
- Broker 1在200s内完成分区平衡所需的带宽限制值=100/200=0.5MB/s
- Broker 2在200s内完成分区平衡所需的带宽限制值=（100+100）/200=1MB/s
综上所述，若想要在200s内完成分区平衡任务，带宽限制值应设为大于等于1.5MB/s。由于控制台的带宽限制只能是整数，因此带宽限制值应设为大于等于2MB/s。
**场景二：Topic1有2分区1副本，Topic2有2分区1副本，** **Leader副本分布在不同Broker上，如[表6]所示，Topic1和Topic2分别需要新增1个副本** **，如[表7]所示。**
 表6分区平衡前Topic分区的副本分布 
| Topic名称  | 分区名称 | Leader副本所在Broker | Follower副本所在Broker |
|:---|:---|:---|:---|
| Topic1    | 0   | 0                | 0                  |
| Topic1    | 1  | 1                | 1                  |
| Topic2 | 0   | 1               | 1                  |
| Topic2  | 1 | 2               | 2               |
   
 表7分区平衡后Topic分区的副本分布 
| Topic名称   | 分区名称 | Leader副本所在Broker | Follower副本所在Broker |
|:---|:---|:---|:---|
| Topic1    | 0    | 0               | 0，2                 |
| Topic1   | 1  | 1               | 1，2                |
| Topic2   | 0  | 1                 | 1，2                 |
| Topic2 | 1   | 2              | 2，0                |
   
图8场景二分区平衡图   
![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000001404290946.png "点击放大")
如[图8]所示，Broker 1中只有Leader副本，Broker 0和Broker 2中存在Leader副本和Follower副本，由于Leader副本的限流和Follower副本限流分开计算，Broker 0和Broker 2需要分别计算Leader副本的限流和Follower副本限流。由此得出以下数据：
- Broker 0作为Leader副本在200s内完成分区平衡所需的带宽限制值=100/200=0.5MB/s
- Broker 0作为Follower副本在200s内完成分区平衡所需的带宽限制值=100/200=0.5MB/s
- Broker 1在200s内完成分区平衡所需的带宽限制值=（100+100）/200=1MB/s
- Broker 2作为Leader副本在200s内完成分区平衡所需的带宽限制值=100/200=0.5MB/s
- Broker 2作为Follower副本在200s内完成分区平衡所需的带宽限制值=（100+100+100）/200=1.5MB/s
综上所述，若想要在200s内完成分区平衡任务，带宽限制值应设为大于等于1.5MB/s。由于控制台的带宽限制只能是整数，因此带宽限制值应设为大于等于2MB/s。
**场景三：Topic1有1分区2副本，Topic2有1分区2副本，** **所有Leader副本在同一个Broker上，如[表8]所示，Topic1需要新增1个副本** **，Topic1上有生产消息造成的副本同步** **，如[表9]所示。**
 表8分区平衡前Topic分区的副本分布 
| Topic名称  | 分区名称 | Leader副本所在Broker | Follower副本所在Broker |
|:---|:---|:---|:---|
| Topic1 | 0    | 0             | 0，1                 |
| Topic2     | 0    | 0             | 0，1                 |
   
 表9分区平衡后Topic分区的副本分布 
| Topic名称 | 分区名称 | Leader副本所在Broker | Follower副本所在Broker |
|:---|:---|:---|:---|
| Topic1 | 0    | 0                 | 0，1，2              |
| Topic2   | 0       | 0                | 0，1                |
   
图9场景三分区平衡图   
![](https://support.huaweicloud.com/usermanual-kafka/zh-cn_image_0000001454518289.png "点击放大")
如[图9]所示，有1个副本由于分区平衡需要从Broker 0拉取数据，另1个副本由于生产消息需要从Broker 0拉取数据，带宽限制不会区分是正常的生产消息造成的副本同步还是分区平衡造成的副本同步，因此两者的流量都会被限流统计。由此得出以下数据：
- Broker 0在200s内完成分区平衡所需的带宽限制值=（100MB+700KB/s\*200s）/200s+700KB/s=1.9MB/s
- Broker 2在200s内完成分区平衡所需的带宽限制值=100/200=0.5MB/s
综上所述，若想要在200s内完成分区平衡任务，带宽限制值应设为大于等于1.9MB/s。由于控制台的带宽限制只能是整数，因此带宽限制值应设为大于等于2MB/s。
#### 相关文档
- 如果您希望通过API修改分区平衡，请参考[Kafka实例开始分区平衡任务](https://support.huaweicloud.com/api-kafka/CreateKafkaReassignmentTask.html)。
- 如果您想要了解不同分区间业务数据不均衡的原因和处理措施，请参考[业务数据不均衡处理建议](https://support.huaweicloud.com/bestpractice-kafka/Kafka_bp_0008.html)。
 
