top of page
Foto do escritorRafael Natali

Reatribuição Automática de Partições em um Cluster Apache Kafka



Quando você precisa reatribuir uma partição para outro broker ou brokers, a ferramenta kafka-reassign-partitions é muito útil. Ela é particularmente eficaz para reatribuir um pequeno número de tópicos. No entanto, observei algumas limitações após trabalhar na expansão de um cluster com mais de 5.000 tópicos.


Para realizar a reatribuição, é necessário executar três comandos distintos e criar dois arquivos JSON para cada reatribuição. Agora, imagine fazer isso para 5.000 tópicos! Embora seja possível construir um único arquivo JSON com uma lista de todos os tópicos e usar a opção `--throttle` para controlar a largura de banda, essa abordagem poderia potencialmente perturbar o ambiente. O que eu queria era reatribuir os tópicos um de cada vez e manter o controle sobre quais tópicos estavam sendo reatribuídos.


Foi precisamente o desafio que eu e meu colega Bruno Costa enfrentamos na semana passada. Nosso objetivo era reatribuir um tópico de cada vez, minimizando qualquer potencial impacto nos produtores e consumidores em execução, ao mesmo tempo que automatizávamos o processo. Como resultado, desenvolvemos um script Bash que simplifica a redistribuição das partições do Kafka. Este script pode ser utilizado para diversos fins, incluindo manutenção, escalonamento ou otimização de clusters.


#!/bin/bash
set +xoe pipefail

#################################################################
# 
# This script uses Kafka's partition reassignment tool to move partitions across brokers.
# Kafka Docs reference:
# https://kafka.apache.org/26/documentation.html#basic_ops_cluster_expansion
#
# Usage:
#
# Create a text file (kafka-topics.txt) with the list of Kafka topics to reassign
# chmod +x ./kafka-reassign.sh
# ./kafka-reassign.sh
#################################################################

output_dir="./output"
[ -d $output_dir ] || mkdir $output_dir

banner()
{
  echo "+------------------------------------------+"
  printf "| %-40s |\n" "`date`"
  printf "| %s \n" "${@//[$'\t\r\n']}"
  echo "+------------------------------------------+"
}

input="kafka-topics.txt"
while IFS= read -r line
do
  banner "Starting Topic ${line//[$'\t\r\n']}"

  echo -e "\nReplacing topic in JSON template"
  sed -e "s/<TOPIC>/${line//[$'\t\r\n']}/g" template.json > $output_dir/topics.json

  echo -e "\nGenerating and cleaning reassign.json"
  kafka-reassign-partitions --bootstrap-server ${BOOTSTRAP_SERVER} --topics-to-move-json-file $output_dir/topics.json --broker-list "0,1,2,3,4"  --generate  | awk '/Proposed partition reassignment configuration/{c=NR+2}(NR<=c){print}' | awk NR\>1 > $output_dir/reassign.json 
  
  echo -e "\nExecuting reassignment"
  kafka-reassign-partitions --bootstrap-server ${BOOTSTRAP_SERVER}  --reassignment-json-file $output_dir/reassign.json  --execute 
  
  echo -e "\nVerifying reassignment"
  kafka-reassign-partitions --bootstrap-server ${BOOTSTRAP_SERVER}  --reassignment-json-file $output_dir/reassign.json  --verify 
  count=$(kafka-reassign-partitions --bootstrap-server ${BOOTSTRAP_SERVER}  --reassignment-json-file $output_dir/reassign.json  --verify  | grep -o "still in progress" | wc -l)
  echo "partition reassignment in progress: $count"
  while [ $count -gt 0 ]
  do
    sleep 5
    count=$(kafka-reassign-partitions --bootstrap-server ${BOOTSTRAP_SERVER}  --reassignment-json-file $output_dir/reassign.json --verify | grep -o "still in progress" | wc -l)
    echo "partition reassignment in progress: $count"
  done
done < "$input"

Você pode fazer o download do script aqui.

Aqui está uma descrição de cada parte do script e o que ela faz:


1. `set +xoe pipefail`: Essas são opções de shell. `+x` desliga a saída de depuração, `o` garante que o script saia se algum comando retornar um status não zero, e `e` assegura que, se parte de um pipeline falhar, o pipeline inteiro falhe.


2. O script inclui uma breve descrição de seu propósito e uso. Ele espera que um arquivo chamado `kafka-topics.txt` contenha uma lista de tópicos do Kafka a serem reatribuídos.


3. output_dir="./output": Isso define a variável `output_dir` como o diretório onde o script armazenará arquivos temporários e registros.


4. A função `banner()` imprime um banner carimbado com a hora no console para indicar quando uma nova reatribuição de tópicos está começando.


5. O script lê a lista de tópicos do Kafka do arquivo `kafka-topics.txt`, um por um, e executa as seguintes etapas para cada tópico:


- Cria um arquivo JSON chamado `topics.json` com base em um modelo `template.json`, substituindo `<TOPIC>` pelo nome real do tópico.

- Usa a ferramenta `kafka-reassign-partitions` para gerar um plano de reatribuição e armazena-o em `reassign.json`. Este plano especifica como as partições do Kafka devem ser movidas entre os brokers.

- Executa a reatribuição, movendo efetivamente as partições de acordo com o plano.

- Verifica o status da reatribuição e aguarda até que ela seja concluída.


O script repete essas etapas para cada tópico listado no `kafka-topics.txt`. Ele também continua verificando o status da reatribuição até que não esteja mais "em progresso" antes de passar para o próximo tópico.



Resultados


Usando este script, conseguimos reatribuir com sucesso 4.923 tópicos em apenas cerca de três dias, tudo isso sem causar qualquer interrupção para produtores e consumidores.


Conclusão


Isso marca a primeira versão do script, e continuaremos a aprimorá-lo conforme necessário. Para obter detalhes mais abrangentes sobre a ferramenta `kafka-reassign-partitions` e como ajustar seu uso para o seu cenário específico, recomendo consultar a documentação do Kafka. Isso permitirá fazer refinamentos e otimizações adicionais de acordo com suas necessidades.







13 visualizações0 comentário

Comments


bottom of page