ES分片從新路由解決分片不平衡問題

一、發現問題html

根據kinbana的monitor發現ES集羣的索引分片分佈不均勻,硬盤使用也不平衡。node

很奇怪分片少的硬盤空間還用得多,而分片多的硬盤反而用得少,還沒搞清楚緣由,ES會本身平衡集羣分片,因爲某個節點分片少,會不停的往這個節點建分片,致使硬盤空間差距愈來愈大,這個問題影響到了存儲,必需要解決。shell

二、查找解決方案json

https://www.elastic.co/guide/en/elasticsearch/reference/6.3/cluster-reroute.htmlbash

根據官方文檔能夠從新路由,移動分片以達到分片平衡,但因爲手動執行命令太慢太累了,因而決定寫個腳本,app

三、最終解決方案:腳本批量移動curl

shell腳本:查找節點重複分片並從新路由(移動分片)elasticsearch

#!/bin/bash

declare -A node_group=(
  ["es-node-01"]="es-node-02 es-node-03 es-node-04 es-node-05 es-node-06 es-node-07"
  ["es-node-02"]="es-node-01 es-node-03 es-node-04 es-node-05 es-node-06 es-node-07"
  ["es-node-03"]="es-node-01 es-node-02 es-node-04 es-node-05 es-node-06 es-node-07"
  ["es-node-04"]="es-node-01 es-node-02 es-node-03 es-node-05 es-node-06 es-node-07"
  ["es-node-05"]="es-node-01 es-node-02 es-node-03 es-node-04 es-node-06 es-node-07"
  ["es-node-06"]="es-node-01 es-node-02 es-node-03 es-node-04 es-node-05 es-node-07"
  ["es-node-07"]="es-node-01 es-node-02 es-node-03 es-node-04 es-node-05 es-node-06"
)

function get_to_nodes(){
  IFS=', ' read -r -a array <<< "$1"
  count=$2
  size=${#array[@]}

  r=$RANDOM
  start=`expr $r % $size`
  for ((i=0;i<$count;i++))
  do
    idx=`expr $start + $i`
    if [[ $idx -ge $size ]]; then
      idx=`expr $idx % $size`
    fi
    result[$i]=${array[$idx]}
  done

  echo "${result[@]}"
}

pattern=$1

src_file=".index_shards"
re_file=".repeat_shards"

server="http://localhost:9200"
# 根據參數傳入的索引pattern獲取分片信息
curl -s -XGET "${server}/_cat/shards/${pattern}?v&h=index,node,ip,shard,prirep,state,store,unassigned.reasons" > $src_file
# 調awk腳本提取單節點有重複分片的索引
awk -f extract.awk $src_file |sort > $re_file

index=""
from_node=""
to_node=""

for line in $(cat $re_file)
do 
  #line=${line//,/ }
  IFS=', ' read -r -a line <<< "$line"
  if [[ ${#line[@]} -eq 3 ]]; then
    #printf "${line[0]}, ${line[1]}, ${line[2]} \n"
    index=${line[0]}
    from_node=${line[1]}
    total=${line[2]}
    count=`expr $total - 1`
    to_nodes=($(get_to_nodes "${node_group[$from_node]}" $count))
    
    shards=($(grep -E "${index}\s+${from_node}" $src_file|awk '$5 =="p" {s=s" "$4}END{print s}'))

    for idx in "${!to_nodes[@]}"
    do
      shard=${shards[$idx]}
      to_node=${to_nodes[$idx]}
      cmd="curl -s -XPOST -H 'Content-Type: application/json' '${server}/_cluster/reroute?filter_path=acknowledged' \
-d '{\"commands\":[{\"move\":{\"index\":\"${index}\",\"shard\":${shard},\"from_node\":\"${from_node}\",\"to_node\":\"${to_node}\"}}]}'"
      #echo "${index}\s+${from_node}, $total-${shards[@]}, $to_node: $cmd"
      rs=`eval $cmd`
      echo "move $index shard $shard from $from_node to $to_node: $rs"
      #exit 0
    done
  fi
  #exit 0
done

awk腳本:提取重複分片信息ide

#!/bin/awk -f

$5 == "p" {sum[$1","$2]++}END{for(i in sum) if(sum[i]>1) printf("%s,%d\n",i,sum[i])}

四、執行ui

# 從新路由平衡2019年2月的分片
bash -e ./reroute.sh *-2019.02.*

五、處理結果

還沒執行完。。。。後面補處理結果

相關文章
相關標籤/搜索