checknodes.sh 5.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. #!/bin/bash
  2. ################################################################################
  3. # Authors: @jytou (https://git.duniter.org/jytou)
  4. # Modified by Fred (support@qo-op.com) to modifiy silkaj constant with best server
  5. # Version: 0.1
  6. # License: AGPL-3.0 (https://choosealicense.com/licenses/agpl-3.0/)
  7. ################################################################################
  8. # Checks the current block number of nodes.txt (is run in parallel) and output random (from last synchronized) node
  9. # pip3 install duniterpy
  10. # pip3 install silkaj --user
  11. checkonenode()
  12. {
  13. # Timeout in seconds for https nodes
  14. httpsTimeout=1
  15. # Timeout in seconds for http nodes
  16. httpTimeout=1
  17. node=$1
  18. watched=$2
  19. outfile=$3
  20. # Curl: -m timeout, -k ignore SSL certificate errors
  21. cur=`echo "$( { curl -m $httpsTimeout -k https://$node/blockchain/current; } 2>&1 )"`
  22. n=$node
  23. if [[ "$cur" != *issuersFrameVar* ]]
  24. then
  25. # It failed in https, maybe try http?
  26. cur=`echo "$( { curl -m $httpTimeout http://$node/blockchain/current; } 2>&1 )"`
  27. if [[ "$cur" == *issuersFrameVar* ]]
  28. then
  29. # Indicate that the node is http
  30. n="$n-(http)"
  31. fi
  32. fi
  33. if [[ "$cur" != *issuersFrameVar* ]]
  34. then
  35. # The node didn't respond on time
  36. cur="ERROR"
  37. else
  38. # The node did respond - grab the block number and hash of the block as key
  39. cur="`echo "$cur"|grep '^ "number": '|awk '{print $2}'|awk -F, '{print $1}'`-`echo "$cur"|grep '^ "hash": '|awk '{print $2}'|awk '{print substr($1,2,13)}'`"
  40. fi
  41. if [[ $watched =~ .*#$node#.* ]]
  42. then
  43. # The node is a watched node, add some bold
  44. n="\e[1m$n\e[0m"
  45. fi
  46. # Put the result into the file
  47. echo "$cur $n">$outfile
  48. # Notify that we're done here
  49. touch $outfile.done
  50. }
  51. # Temp dir where results are stored
  52. DIR=/tmp/gnodewatch
  53. export DIR
  54. mkdir -p $DIR/chains
  55. ###########
  56. # BANNISH DUNITER NODE?
  57. # TODO: silkaj evolution!! Better CLI integration to make!
  58. # Duniter Node is too slow or behave badly, remove it from nodes.txt list
  59. BAN=$1
  60. if [[ "$BAN" == "BAN" ]]; then
  61. # Get actual Duniter node used by silkaj
  62. SERVER=$(cat ./silkaj/src/constants.py | grep G1_DEFAULT_ENDPOINT | awk '{print $3}' | sed s/\"\,//g | sed s/\"//g)
  63. [[ ! $(grep $SERVER:443 shell/bad.nodes.txt) ]] && echo $SERVER:443 >> shell/bad.nodes.txt
  64. sed -i "/$SERVER:443/d" ./shell/good.nodes.txt
  65. echo "$SERVER:443 IS NOW in ./shell/bad.nodes.txt"
  66. fi
  67. ### nodes.txt EMPTYNESS CARE
  68. NBgood=$(cat ./shell/good.nodes.txt | wc -l)
  69. NBbad=$(cat ./shell/bad.nodes.txt | wc -l)
  70. if [[ $NBgood -le $NBbad ]]; then
  71. echo "" > ./shell/good.nodes.txt
  72. echo "" > ./shell/bad.nodes.txt
  73. # TODO: Each decentralized App must have a source for its confidence to be UP and running and publishing latest code for our concensus behaviour!
  74. echo "___ REFRESH ./shell/nodes.txt from g1.duniter.org:443 ___"
  75. curl -s https://g1.duniter.org/network/peers | jq '.peers[] | .endpoints' | grep BMAS | awk '{print $2,$3}' | sed s/\"//g | sed s/\,//g | sed s/\ /:/g > "./shell/nodes.txt"
  76. echo $(cat "./shell/nodes.txt")
  77. fi
  78. ###########
  79. # CONTINUE
  80. # Grab the nodes we are actively watching - they will be in bold in the final output
  81. watched=`grep -v "#" ./shell/nodes.txt|egrep "\!$"|awk '{print "#" $1 "#"}'`
  82. # All nodes we are watching
  83. nodes=`grep -v "#" ./shell/nodes.txt|awk '{print $1}'`
  84. # The index to generate separate file names
  85. index=0
  86. # Wipe out the output directory
  87. rm $DIR/*out $DIR/*done $DIR/chains/* $DIR/NODE.* 2>/dev/null
  88. # Query all nodes in parallel
  89. for node in $nodes
  90. do
  91. checkonenode $node "$watched" $DIR/$index.out &
  92. ((index++))
  93. done
  94. # Wait a little for the first files to be created
  95. sleep 1s
  96. # Wait for all the threads to report they are done
  97. while [ `ls $DIR/*done|wc -l` -lt $index ]
  98. do
  99. sleep 1s
  100. done
  101. # Grab all results
  102. curs=`cat $DIR/*out|sort`
  103. # Extract all forks, excluding all errors
  104. chains="`echo "$curs"|grep -v ERROR|awk '{print $1}'|sort -r|uniq`"
  105. # Count the number of chains and output most recent consensus to "good.nodes.txt"
  106. nb=0
  107. for chain in $chains
  108. do
  109. echo "$curs" | egrep "^$chain " | awk '{print $2}' >> $DIR/chains/$nb;
  110. ((nb++))
  111. done
  112. longchain=$(ls -S /tmp/gnodewatch/chains/ | head -n 1)
  113. cp /tmp/gnodewatch/chains/$longchain "./shell/good.nodes.txt"
  114. #####################################################################################
  115. # ASK peers to all good.nodes.txt
  116. #for node in $(cat ./shell/good.nodes.txt); do
  117. # NANODATE=$(date +%s%N);
  118. # DUN="https://$(echo $node| cut -d ":" -f 1)";
  119. # curl -s -o $DIR/NODE.$NANODATE.$node ${DUN}/network/peers;
  120. #done
  121. # REFRESH from all known peers NEW nodes.txt
  122. #cat /tmp/gnodewatch/NODE.* | jq '.peers[] | .endpoints' | grep BMAS | awk '{print $2,$3}' | sed s/\"//g | sed s/\,//g | sed s/\ /:/g | sort | uniq > "./shell/nodes.txt"
  123. #####################################################################################
  124. # Output Random actual best node
  125. # Compare with ./shell/bad.nodes.txt
  126. while [[ "$BAD" == "$DUNITER" ]]; do
  127. DUNITER=$(shuf "./shell/good.nodes.txt" | head -n 1)
  128. BAD=$(grep -Rw "$DUNITER" ./shell/bad.nodes.txt)
  129. done
  130. ################# MODIFY silkaj constants.py
  131. silkaj=$(echo $DUNITER | cut -d ":" -f 1)
  132. if [[ "$silkaj" != "" && "$silkaj" != "https" ]]; then
  133. #echo "PUT $silkaj SILKAJ PARAM"
  134. cat ./silkaj/src/constants.default.py | sed s/duniter-g1.p2p.legal/$silkaj/g > ./silkaj/src/constants.py
  135. else
  136. echo "RESTORE DEFAULT SILKAJ PARAM"
  137. cp -f ./silkaj/src/constants.default.py ./silkaj/src/constants.py
  138. fi
  139. echo $DUNITER