From dfe386d92fb911d8fc21c48817618097b74172c5 Mon Sep 17 00:00:00 2001 From: Leopold Joy Date: Sat, 12 Jan 2019 05:12:08 -0500 Subject: [PATCH 1/4] implement combination of withdraw and delegation messages on auto-delegate.sh script --- auto-delegate.sh | 103 +++++++++++++++++++++++++++++++++++++++++------ 1 file changed, 91 insertions(+), 12 deletions(-) diff --git a/auto-delegate.sh b/auto-delegate.sh index 261ce13..cead100 100644 --- a/auto-delegate.sh +++ b/auto-delegate.sh @@ -4,28 +4,107 @@ # NOTE: if you have not yet set any env vars, then you must first run: systemctl edit auto_withdraw_delegate.service # which will generate the above file (at /etc/systemd/system/myservice.service.d/myenv.conf) +echo "Setting (fake) initial historical interval stake earnings..." +last_10_interval_earnings[0]=100 + +remaining_stake_from_delegation_before_last=0 + +filePath="./txn.json" + while true do num_unconfirmed_txs=$(curl -v --silent curl localhost:26657/num_unconfirmed_txs --stderr - | grep n_txs | cut -c15) + echo "Number of unconfirmed txs: $num_unconfirmed_txs" if [[ ($num_unconfirmed_txs -gt 0)]] then - echo "There is a TX in the mempool" - echo "..." - sleep 60s + echo "There is a TX in the mempool" + echo "..." + sleep 60s else - amount_steak=$(sudo -u gaiad /opt/go/bin/gaiacli --home=/opt/gaiacli query account cosmos1844lltc96kxkm5mq03my90se4cdssewmh77shu --chain-id=game_of_stakes_3 --trust-node=true | jq -r '.value.coins[0].amount') - echo "Number of stakes: ${amount_steak}" - if [[ $amount_steak > 0 && $amount_steak != "null" && ($amount_steak -lt 10000000)]] + + # Get the remaining undelegated STAKE (not delegated in the last transaction due to estimation inaccuracy) + remaining_stake_left_from_last_delegation=$(sudo -u gaiad /opt/go/bin/gaiacli --home=/opt/gaiacli query account cosmos1844lltc96kxkm5mq03my90se4cdssewmh77shu --chain-id=game_of_stakes_3 --trust-node=true | jq -r '.value.coins[0].amount') + + # Check that this is in fact STAKE not photinos + if [[($remaining_stake_left_from_last_delegation -gt 10000000)]] + then + # Since it was photinos, set equal to zero since there were no STAKE left following the last transaction + remaining_stake_left_from_last_delegation=0 + fi + echo "STAKE remaining from last delegation: $remaining_stake_left_from_last_delegation" + + # Get existing min value (from last transaction) + last_min_from_last_10="$(echo "${last_10_interval_earnings[@]}" | sed -e $'s/ /\\\n/g' | sort -n | head -n1)" + + echo "Existing (old) 10 most recent interval earnings: " + printf '%s, ' "${last_10_interval_earnings[@]}\n" + echo "Existing minimum value (from last 10): $last_min_from_last_10" + + # Check if we overshot with the last estimation + if [[($remaining_stake_left_from_last_delegation -gt $last_min_from_last_10)]] then - duration=$(( SECONDS - start )) - echo "$duration seconds since last TX call" - echo "Sending transaction to delegate ${amount_steak} stakes" - echo "${GAIA_KEY}" | sudo -u gaiad /opt/go/bin/gaiacli tx stake delegate --home=/opt/gaiacli --amount=${amount_steak}STAKE --from=game-of-stake-key-validator4 --validator=cosmosvaloper1844lltc96kxkm5mq03my90se4cdssewmj229m0 --chain-id=game_of_stakes_3 --fee=1000photinos | start=$SECONDS + # In this case we overshot the actual accrued STAKE since our estimate was just below the actual amount. + # The total amount of stake left from our last delegation attempt, minus the STAKE left over from the + # delegation before that, represents the "corrected" amount for this last delegation. + corrected_total_accrued_before_last_delegation=$((remaining_stake_left_from_last_delegation-remaining_stake_from_delegation_before_last)) + echo "Overshot (didn't effectively delegate) actual accrued STAKE for last estimation. This is how much STAKE there was: $corrected_total_accrued_before_last_delegation" else - echo "Sending transaction to withdraw stakes" - echo "${GAIA_KEY}" | sudo /opt/go/bin/gaiacli --home=/opt/gaiacli tx dist withdraw-rewards --async --is-validator --from=game-of-stake-key-validator4 --chain-id=game_of_stakes_3 --trust-node + # In this case we had a good estimation (marginally undershot the actual amount of accrued STAKE). + # Now we calculate the actual, "corrected", amount from our last delegation: + # (Amount that should've been delegated last time) = (amount that was delegated last time) + (remaining stake in balance that wasn't delegated) + corrected_total_accrued_before_last_delegation=$((last_min_from_last_10+remaining_stake_left_from_last_delegation)) + echo "Undershot actual accrued STAKE for last estimation (by $remaining_stake_left_from_last_delegation). Exact amount: $corrected_total_accrued_before_last_delegation" fi + + # Prepend the correct accrued STAKE from last time to the last 10 array + last_10_interval_earnings=("${corrected_total_accrued_before_last_delegation}" "${last_10_interval_earnings[@]}") + + # Unset the last element of the historical record (to limit array to the last 10 values) + unset last_10_interval_earnings[10] + + # Calculate new min from past 10 + new_min_from_last_10="$(echo "${last_10_interval_earnings[@]}" | sed -e $'s/ /\\\n/g' | sort -n | head -n1)" + + # Save remaining stake from last delegation for next delegation calculations (for estimation correction) + remaining_stake_from_delegation_before_last=$remaining_stake_left_from_last_delegation + + echo "Updated 10 most recent interval earnings:" + printf '%s, ' "${last_10_interval_earnings[@]}\n" + echo "Updated minimum value (from last 10): $new_min_from_last_10" + echo "Extra STAKE to delegate with this transaction (from under-estimation on last transaction): $remaining_stake_left_from_last_delegation" + + total_to_delegate=$((new_min_from_last_10+remaining_stake_left_from_last_delegation)) + + echo "About to withdraw (all STAKE) and delegate: $total_to_delegate STAKE" + + # Create withdrawal transaction + withdrawal_txn=$(sudo /opt/go/bin/gaiacli --home=/opt/gaiacli tx dist withdraw-rewards --async --is-validator --from=game-of-stake-key-validator4 --chain-id=game_of_stakes_3 --fee=1000photinos --trust-node --generate-only) + + # Create delegation transaction and save withdrawal message to variable + delegation_txn=$(sudo -u gaiad /opt/go/bin/gaiacli tx stake delegate --async --home=/opt/gaiacli --amount=${total_to_delegate}STAKE --from=game-of-stake-key-validator4 --validator=cosmosvaloper1844lltc96kxkm5mq03my90se4cdssewmj229m0 --chain-id=game_of_stakes_3 --fee=1000photinos --generate-only) + delegation_msg=$(echo $delegation_txn | jq -r '.value.msg[0]') + + # Combine the delegation message with the withdrawal transaction to create the final transaction (with both messages) + withdrawal_and_delegation_txn=$(echo $withdrawal_txn | jq ".value.msg[1] |= . + $delegation_msg") + + echo "Saving generated withdrawal/delegation transaction to $filePath..." + + # Write combined transaction to file + echo "$withdrawal_and_delegation_txn" | sudo tee $filePath + + # Sign combined transaction + signed_txn=$(echo "${GAIA_KEY}" | sudo -u gaiad /opt/go/bin/gaiacli --home=/opt/gaiacli tx sign $filePath --trust-node --account-number 0 --name game-of-stake-key-validator4 --fee=1000photinos --chain-id game_of_stakes_3 --from=game-of-stake-key-validator4) + + echo "Transaction signed! Saving signed transaction to $filePath..." + + # Write signed transaction to file + echo "$signed_txn" | sudo tee $filePath + + # Broadcast the signed transaction + echo "Broadcasting transaction... Result:" + broadcast_result=$(sudo -u gaiad /opt/go/bin/gaiacli --home=/opt/gaiacli tx broadcast $filePath --account-number 0 --chain-id game_of_stakes_3 --fee=1000photinos --from=game-of-stake-key-validator4 --trust-node) + sleep 5m fi done From 60f64cef097541a52535c5b424b259cc33e547fb Mon Sep 17 00:00:00 2001 From: Leopold Joy Date: Sat, 12 Jan 2019 05:58:53 -0500 Subject: [PATCH 2/4] clean up withdrawal command flags and file name variable --- auto-delegate.sh | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/auto-delegate.sh b/auto-delegate.sh index cead100..c4abf33 100644 --- a/auto-delegate.sh +++ b/auto-delegate.sh @@ -9,7 +9,7 @@ last_10_interval_earnings[0]=100 remaining_stake_from_delegation_before_last=0 -filePath="./txn.json" +combo_txn_file="./txn.json" while true do @@ -79,7 +79,7 @@ do echo "About to withdraw (all STAKE) and delegate: $total_to_delegate STAKE" # Create withdrawal transaction - withdrawal_txn=$(sudo /opt/go/bin/gaiacli --home=/opt/gaiacli tx dist withdraw-rewards --async --is-validator --from=game-of-stake-key-validator4 --chain-id=game_of_stakes_3 --fee=1000photinos --trust-node --generate-only) + withdrawal_txn=$(sudo /opt/go/bin/gaiacli --home=/opt/gaiacli tx dist withdraw-rewards --is-validator --from=game-of-stake-key-validator4 --chain-id=game_of_stakes_3 --fee=1000photinos --trust-node --generate-only) # Create delegation transaction and save withdrawal message to variable delegation_txn=$(sudo -u gaiad /opt/go/bin/gaiacli tx stake delegate --async --home=/opt/gaiacli --amount=${total_to_delegate}STAKE --from=game-of-stake-key-validator4 --validator=cosmosvaloper1844lltc96kxkm5mq03my90se4cdssewmj229m0 --chain-id=game_of_stakes_3 --fee=1000photinos --generate-only) @@ -88,22 +88,22 @@ do # Combine the delegation message with the withdrawal transaction to create the final transaction (with both messages) withdrawal_and_delegation_txn=$(echo $withdrawal_txn | jq ".value.msg[1] |= . + $delegation_msg") - echo "Saving generated withdrawal/delegation transaction to $filePath..." + echo "Saving generated withdrawal/delegation transaction to $combo_txn_file..." # Write combined transaction to file - echo "$withdrawal_and_delegation_txn" | sudo tee $filePath + echo "$withdrawal_and_delegation_txn" | sudo tee $combo_txn_file # Sign combined transaction - signed_txn=$(echo "${GAIA_KEY}" | sudo -u gaiad /opt/go/bin/gaiacli --home=/opt/gaiacli tx sign $filePath --trust-node --account-number 0 --name game-of-stake-key-validator4 --fee=1000photinos --chain-id game_of_stakes_3 --from=game-of-stake-key-validator4) + signed_txn=$(echo "${GAIA_KEY}" | sudo -u gaiad /opt/go/bin/gaiacli --home=/opt/gaiacli tx sign $combo_txn_file --trust-node --account-number 0 --name game-of-stake-key-validator4 --fee=1000photinos --chain-id game_of_stakes_3 --from=game-of-stake-key-validator4) - echo "Transaction signed! Saving signed transaction to $filePath..." + echo "Transaction signed! Saving signed transaction to $combo_txn_file..." # Write signed transaction to file - echo "$signed_txn" | sudo tee $filePath + echo "$signed_txn" | sudo tee $combo_txn_file # Broadcast the signed transaction echo "Broadcasting transaction... Result:" - broadcast_result=$(sudo -u gaiad /opt/go/bin/gaiacli --home=/opt/gaiacli tx broadcast $filePath --account-number 0 --chain-id game_of_stakes_3 --fee=1000photinos --from=game-of-stake-key-validator4 --trust-node) + broadcast_result=$(sudo -u gaiad /opt/go/bin/gaiacli --home=/opt/gaiacli tx broadcast $combo_txn_file --account-number 0 --chain-id game_of_stakes_3 --fee=1000photinos --from=game-of-stake-key-validator4 --trust-node) sleep 5m fi From edec0a1a7cb9889e2b360c789a77231fb6a034c7 Mon Sep 17 00:00:00 2001 From: Leopold Joy Date: Fri, 18 Jan 2019 01:49:13 -0500 Subject: [PATCH 3/4] fix auto delegation script bug leading to zero / negative STAKE delegation values --- auto-delegate.sh | 51 ++++++++++++++++++++++++++++++++++++------------ 1 file changed, 38 insertions(+), 13 deletions(-) diff --git a/auto-delegate.sh b/auto-delegate.sh index cead100..09d63dd 100644 --- a/auto-delegate.sh +++ b/auto-delegate.sh @@ -5,7 +5,7 @@ # which will generate the above file (at /etc/systemd/system/myservice.service.d/myenv.conf) echo "Setting (fake) initial historical interval stake earnings..." -last_10_interval_earnings[0]=100 +last_10_interval_earnings[0]=260 remaining_stake_from_delegation_before_last=0 @@ -38,23 +38,48 @@ do last_min_from_last_10="$(echo "${last_10_interval_earnings[@]}" | sed -e $'s/ /\\\n/g' | sort -n | head -n1)" echo "Existing (old) 10 most recent interval earnings: " - printf '%s, ' "${last_10_interval_earnings[@]}\n" + printf '%s, ' "${last_10_interval_earnings[@]}" + echo "" echo "Existing minimum value (from last 10): $last_min_from_last_10" # Check if we overshot with the last estimation - if [[($remaining_stake_left_from_last_delegation -gt $last_min_from_last_10)]] + if [[($remaining_stake_left_from_last_delegation -ge $last_min_from_last_10)]] + then + # In this case we overshot the actual accrued STAKE since our estimate was just below the actual amount. + echo "Overshot (didn't effectively delegate) actual accrued STAKE for last estimation." + # To determine the "corrected" amount for the last delegation, we first check if the amount of stake + # from the delegation attempt before last is equal to the amount of stake left from our last delegation + # attempt (since if they're equal it means that the last transaction failed): + if [[($remaining_stake_from_delegation_before_last -eq $remaining_stake_left_from_last_delegation)]] + then + # Because the last transaction failed, we have no new information about how much stake was left from the + # last transaction since the withdraw call didn't go through (hence why they're equal). Thus, since we do + # not have sufficient informaton and only know that we overshow the target, we simply correct by reducing + # the current minimum value by 10%: + corrected_total_accrued_before_last_delegation=$(echo $last_min_from_last_10*9/10 | bc) + echo "They were equal!" + echo "Corrected total = (last 10 min * 0.9)" + # We now check if the amount of stake from the delegation attempt before last is greater than the amount of + # stake left from our last delegation attempt + elif [[($remaining_stake_from_delegation_before_last -gt $remaining_stake_left_from_last_delegation)]] then - # In this case we overshot the actual accrued STAKE since our estimate was just below the actual amount. - # The total amount of stake left from our last delegation attempt, minus the STAKE left over from the - # delegation before that, represents the "corrected" amount for this last delegation. - corrected_total_accrued_before_last_delegation=$((remaining_stake_left_from_last_delegation-remaining_stake_from_delegation_before_last)) - echo "Overshot (didn't effectively delegate) actual accrued STAKE for last estimation. This is how much STAKE there was: $corrected_total_accrued_before_last_delegation" + # The total amount of stake left from our last delegation attempt represents the "corrected" amount + # for this last delegation. + corrected_total_accrued_before_last_delegation=$remaining_stake_left_from_last_delegation + echo "Corrected total = (stake left from last delegation)" else - # In this case we had a good estimation (marginally undershot the actual amount of accrued STAKE). - # Now we calculate the actual, "corrected", amount from our last delegation: - # (Amount that should've been delegated last time) = (amount that was delegated last time) + (remaining stake in balance that wasn't delegated) - corrected_total_accrued_before_last_delegation=$((last_min_from_last_10+remaining_stake_left_from_last_delegation)) - echo "Undershot actual accrued STAKE for last estimation (by $remaining_stake_left_from_last_delegation). Exact amount: $corrected_total_accrued_before_last_delegation" + # The total amount of stake left from our last delegation attempt, minus the STAKE left over from the + # delegation before that, represents the "corrected" amount for this last delegation. + corrected_total_accrued_before_last_delegation=$((remaining_stake_left_from_last_delegation-remaining_stake_from_delegation_before_last)) + echo "Corrected total = (stake left from delegation before last) - (stake left from last delegation)" + fi + echo "This is how much STAKE there was: $corrected_total_accrued_before_last_delegation" + else + # In this case we had a good estimation (marginally undershot the actual amount of accrued STAKE). + # Now we calculate the actual, "corrected", amount from our last delegation: + # (Amount that should've been delegated last time) = (amount that was delegated last time) + (remaining stake in balance that wasn't delegated) + corrected_total_accrued_before_last_delegation=$((last_min_from_last_10+remaining_stake_left_from_last_delegation)) + echo "Undershot actual accrued STAKE for last estimation (by $remaining_stake_left_from_last_delegation). Exact amount: $corrected_total_accrued_before_last_delegation" fi # Prepend the correct accrued STAKE from last time to the last 10 array From ff1359fb579fe7816624b90e35fbd9ac7b7edd6f Mon Sep 17 00:00:00 2001 From: Leopold Joy Date: Mon, 21 Jan 2019 13:02:44 -0500 Subject: [PATCH 4/4] implement fix for bug triggered during repetitive overshoot estimations --- auto-delegate.sh | 69 ++++++++++++++++++++++++++++-------------------- 1 file changed, 40 insertions(+), 29 deletions(-) diff --git a/auto-delegate.sh b/auto-delegate.sh index c9dd066..8954691 100644 --- a/auto-delegate.sh +++ b/auto-delegate.sh @@ -5,9 +5,18 @@ # which will generate the above file (at /etc/systemd/system/myservice.service.d/myenv.conf) echo "Setting (fake) initial historical interval stake earnings..." -last_10_interval_earnings[0]=260 - -remaining_stake_from_delegation_before_last=0 +last_10_interval_earnings[0]=303 +last_10_interval_earnings[1]=319 +last_10_interval_earnings[2]=426 +last_10_interval_earnings[3]=426 +last_10_interval_earnings[4]=336 +last_10_interval_earnings[5]=745 +last_10_interval_earnings[6]=380 +last_10_interval_earnings[7]=380 +last_10_interval_earnings[8]=380 +last_10_interval_earnings[9]=380 + +remaining_stake_from_delegation_before_last=447 combo_txn_file="./txn.json" @@ -47,33 +56,26 @@ do then # In this case we overshot the actual accrued STAKE since our estimate was just below the actual amount. echo "Overshot (didn't effectively delegate) actual accrued STAKE for last estimation." - # To determine the "corrected" amount for the last delegation, we first check if the amount of stake - # from the delegation attempt before last is equal to the amount of stake left from our last delegation - # attempt (since if they're equal it means that the last transaction failed): - if [[($remaining_stake_from_delegation_before_last -eq $remaining_stake_left_from_last_delegation)]] + # As long as the remaining stake from the last delegation is less than the remaining stake from the delegation + # before that, we can calculate the "corrected" amount of STAKE before the last delegation. Otherwise we must + # simply reduce the current minimum value by 5% (since we do not have information to know how much to reduce + # the min by due to the last withdraw transaction failing). + if [[($remaining_stake_from_delegation_before_last -lt $remaining_stake_left_from_last_delegation)]] then + # The total amount of stake left from our last delegation attempt, minus the STAKE left over from the + # delegation before that, represents the "corrected" amount for this last delegation. + corrected_total_accrued_before_last_delegation=$((remaining_stake_left_from_last_delegation-remaining_stake_from_delegation_before_last)) + echo "Corrected total = (stake left from delegation before last) - (stake left from last delegation)" + else # Because the last transaction failed, we have no new information about how much stake was left from the - # last transaction since the withdraw call didn't go through (hence why they're equal). Thus, since we do - # not have sufficient informaton and only know that we overshow the target, we simply correct by reducing - # the current minimum value by 10%: - corrected_total_accrued_before_last_delegation=$(echo $last_min_from_last_10*9/10 | bc) + # last transaction since the withdraw call didn't go through. Thus, since we do + # not have sufficient informaton and only know that we overshot the target, we simply correct by reducing + # the current minimum value by 5%: + corrected_total_accrued_before_last_delegation=$(echo $last_min_from_last_10*19/20 | bc) echo "They were equal!" - echo "Corrected total = (last 10 min * 0.9)" - # We now check if the amount of stake from the delegation attempt before last is greater than the amount of - # stake left from our last delegation attempt - elif [[($remaining_stake_from_delegation_before_last -gt $remaining_stake_left_from_last_delegation)]] - then - # The total amount of stake left from our last delegation attempt represents the "corrected" amount - # for this last delegation. - corrected_total_accrued_before_last_delegation=$remaining_stake_left_from_last_delegation - echo "Corrected total = (stake left from last delegation)" - else - # The total amount of stake left from our last delegation attempt, minus the STAKE left over from the - # delegation before that, represents the "corrected" amount for this last delegation. - corrected_total_accrued_before_last_delegation=$((remaining_stake_left_from_last_delegation-remaining_stake_from_delegation_before_last)) - echo "Corrected total = (stake left from delegation before last) - (stake left from last delegation)" + echo "Corrected total = (last 10 min * 0.95)" fi - echo "This is how much STAKE there was: $corrected_total_accrued_before_last_delegation" + echo "Corrected value: $corrected_total_accrued_before_last_delegation" else # In this case we had a good estimation (marginally undershot the actual amount of accrued STAKE). # Now we calculate the actual, "corrected", amount from our last delegation: @@ -95,11 +97,20 @@ do remaining_stake_from_delegation_before_last=$remaining_stake_left_from_last_delegation echo "Updated 10 most recent interval earnings:" - printf '%s, ' "${last_10_interval_earnings[@]}\n" + printf '%s, ' "${last_10_interval_earnings[@]}" + echo "" echo "Updated minimum value (from last 10): $new_min_from_last_10" echo "Extra STAKE to delegate with this transaction (from under-estimation on last transaction): $remaining_stake_left_from_last_delegation" - total_to_delegate=$((new_min_from_last_10+remaining_stake_left_from_last_delegation)) + # Check if the last withdraw attempt was did not work; if so, multiply the new_min_from_last_10 by two, + # since two windows of delegation will have been missed. + if [[($remaining_stake_left_from_last_delegation -ge $last_min_from_last_10)]] && [[($remaining_stake_from_delegation_before_last -eq $remaining_stake_left_from_last_delegation)]] + then + echo "(Multiply total new_min_from_last_10 by two since we will have accrued two delegation windows worth of STAKE.)" + total_to_delegate=$(((new_min_from_last_10*2)+remaining_stake_left_from_last_delegation)) + else + total_to_delegate=$((new_min_from_last_10+remaining_stake_left_from_last_delegation)) + fi echo "About to withdraw (all STAKE) and delegate: $total_to_delegate STAKE" @@ -107,7 +118,7 @@ do withdrawal_txn=$(sudo /opt/go/bin/gaiacli --home=/opt/gaiacli tx dist withdraw-rewards --is-validator --from=game-of-stake-key-validator4 --chain-id=game_of_stakes_3 --fee=1000photinos --trust-node --generate-only) # Create delegation transaction and save withdrawal message to variable - delegation_txn=$(sudo -u gaiad /opt/go/bin/gaiacli tx stake delegate --async --home=/opt/gaiacli --amount=${total_to_delegate}STAKE --from=game-of-stake-key-validator4 --validator=cosmosvaloper1844lltc96kxkm5mq03my90se4cdssewmj229m0 --chain-id=game_of_stakes_3 --fee=1000photinos --generate-only) + delegation_txn=$(sudo -u gaiad /opt/go/bin/gaiacli tx stake delegate --home=/opt/gaiacli --amount=${total_to_delegate}STAKE --from=game-of-stake-key-validator4 --validator=cosmosvaloper1844lltc96kxkm5mq03my90se4cdssewmj229m0 --chain-id=game_of_stakes_3 --fee=1000photinos --generate-only) delegation_msg=$(echo $delegation_txn | jq -r '.value.msg[0]') # Combine the delegation message with the withdrawal transaction to create the final transaction (with both messages)