diff --git a/spartan/aztec-network/files/cleanup/consolidate-sepolia-balances.sh b/spartan/aztec-network/files/cleanup/consolidate-sepolia-balances.sh deleted file mode 100755 index e39d51fa5897..000000000000 --- a/spartan/aztec-network/files/cleanup/consolidate-sepolia-balances.sh +++ /dev/null @@ -1,47 +0,0 @@ -#!/bin/bash -set -exu - -mnemonic=$1 -# at least 2 accounts are needed for the validator and prover nodes -num_accounts=${2:-"2"} -funding_address=${3:-"0x33D525f5ac95c2BCf98b644738C7d5673480493A"} - -XDG_CONFIG_HOME=${XDG_CONFIG_HOME:-"$HOME/.config"} - -ETHEREUM_RPC_URL=$(echo "$ETHEREUM_HOSTS" | cut -d',' -f1) - -# Install cast if needed -if ! command -v cast &>/dev/null; then - curl -L https://foundry.paradigm.xyz | bash - $HOME/.foundry/bin/foundryup && export PATH="$PATH:$HOME/.foundry/bin" || - $XDG_CONFIG_HOME/.foundry/bin/foundryup && export PATH="$PATH:$XDG_CONFIG_HOME/.foundry/bin" -fi - -# For each index -for i in $(seq 0 $((num_accounts - 1))); do - # Get address and private key for this index - address=$(cast wallet address --mnemonic "$mnemonic" --mnemonic-index $i) - private_key=$(cast wallet private-key --mnemonic "$mnemonic" --mnemonic-index $i) - - # Get balance - balance=$(cast balance $address --rpc-url "$ETHEREUM_RPC_URL") - - if [ "$balance" != "0" ]; then - gas_price=$(cast gas-price --rpc-url "$ETHEREUM_RPC_URL") - gas_price=$((gas_price * 120 / 100)) # Add 20% to gas price - gas_cost=$((21000 * gas_price)) - - # Calculate amount to send (balance - gas cost) - send_amount=$((balance - gas_cost)) - - if [ "$send_amount" -gt "0" ]; then - echo "Sending $send_amount wei from $address to $funding_address" - cast send --private-key "$private_key" --rpc-url "$ETHEREUM_RPC_URL" "$funding_address" \ - --value "$send_amount" --gas-price "$gas_price" --async - else - echo "Balance too low to cover gas costs for $address" - fi - else - echo "No balance in $address" - fi -done diff --git a/spartan/aztec-network/templates/consolidate-balances.yaml b/spartan/aztec-network/templates/consolidate-balances.yaml index 68a34886e313..d7f63aab73bd 100644 --- a/spartan/aztec-network/templates/consolidate-balances.yaml +++ b/spartan/aztec-network/templates/consolidate-balances.yaml @@ -1,3 +1,4 @@ +# NOTE: If script logic below is updated, then scripts/consolidate-sepolia-balances.sh should be updated as well. {{- if .Values.ethereum.execution.externalHosts }} apiVersion: batch/v1 kind: Job @@ -24,9 +25,105 @@ spec: - name: config emptyDir: {} - name: scripts - configMap: - name: {{ include "aztec-network.fullname" . }}-scripts - defaultMode: 0755 + # Use emptyDir instead of ConfigMap to avoid dependency on a resource that might be deleted + emptyDir: {} + initContainers: + - name: create-scripts + image: busybox + command: + - /bin/sh + - -c + - | + cat > /scripts/consolidate-sepolia-balances.sh << 'EOF' + #!/bin/bash + set -eu + + mnemonic=$1 + funding_address=${2:-"0x33D525f5ac95c2BCf98b644738C7d5673480493A"} + + XDG_CONFIG_HOME=${XDG_CONFIG_HOME:-"$HOME/.config"} + + ETHEREUM_RPC_URL=$(echo "$ETHEREUM_HOSTS" | cut -d',' -f1) + + # Install cast if needed + if ! command -v cast &>/dev/null; then + curl -L https://foundry.paradigm.xyz | bash + $HOME/.foundry/bin/foundryup && export PATH="$PATH:$HOME/.foundry/bin" || + $XDG_CONFIG_HOME/.foundry/bin/foundryup && export PATH="$PATH:$XDG_CONFIG_HOME/.foundry/bin" + fi + + # Get the indices to check based on the configuration + validator_key_index_start={{ .Values.aztec.validatorKeyIndexStart }} + prover_key_index_start={{ .Values.aztec.proverKeyIndexStart }} + bot_key_index_start={{ .Values.aztec.botKeyIndexStart }} + + num_validators={{ .Values.validator.replicas }} + num_provers={{ .Values.proverNode.replicas }} + + # Check if bots are enabled + bot_enabled={{ .Values.bot.enabled }} + if [ "$bot_enabled" = "true" ]; then + num_bots={{ .Values.bot.replicas }} + else + num_bots=0 + fi + + # Build an array of indices to check + declare -a indices_to_check + + # Add validator indices + for ((i = 0; i < num_validators; i++)); do + indices_to_check+=($((validator_key_index_start + i))) + done + + # Add prover indices + for ((i = 0; i < num_provers; i++)); do + indices_to_check+=($((prover_key_index_start + i))) + done + + # Add bot indices if enabled + if [ "$bot_enabled" = "true" ]; then + for ((i = 0; i < num_bots; i++)); do + indices_to_check+=($((bot_key_index_start + i))) + done + fi + + echo "Checking balances for ${#indices_to_check[@]} accounts..." + + # For each index in our list + for i in "${indices_to_check[@]}"; do + # Get address and private key for this index + address=$(cast wallet address --mnemonic "$mnemonic" --mnemonic-index $i) + private_key=$(cast wallet private-key --mnemonic "$mnemonic" --mnemonic-index $i) + + # Get balance + balance=$(cast balance $address --rpc-url "$ETHEREUM_RPC_URL") + + if [ "$balance" != "0" ]; then + gas_price=$(cast gas-price --rpc-url "$ETHEREUM_RPC_URL") + gas_price=$((gas_price * 120 / 100)) # Add 20% to gas price + gas_cost=$((21000 * gas_price)) + + # Calculate amount to send (balance - gas cost) + send_amount=$((balance - gas_cost)) + + if [ "$send_amount" -gt "0" ]; then + echo "Sending $send_amount wei from $address (index $i) to $funding_address" + cast send --private-key "$private_key" --rpc-url "$ETHEREUM_RPC_URL" "$funding_address" \ + --value "$send_amount" --gas-price "$gas_price" --async + else + echo "Balance too low to cover gas costs for $address (index $i)" + fi + else + echo "No balance in $address (index $i)" + fi + done + EOF + chmod +x /scripts/consolidate-sepolia-balances.sh + volumeMounts: + - name: scripts + mountPath: /scripts + containers: - name: consolidate-balances {{- include "aztec-network.image" . | nindent 10 }} @@ -39,7 +136,7 @@ spec: - /bin/bash - -c - | - /scripts/consolidate-sepolia-balances.sh "{{ .Values.aztec.l1DeploymentMnemonic }}" {{ add .Values.validator.replicas .Values.proverNode.replicas }} + /scripts/consolidate-sepolia-balances.sh "{{ .Values.aztec.l1DeploymentMnemonic }}" env: - name: ETHEREUM_HOSTS value: "{{ .Values.ethereum.execution.externalHosts }}" diff --git a/spartan/aztec-network/values/ci-sepolia.yaml b/spartan/aztec-network/values/ci-sepolia.yaml index 0d28e12a62d8..d6ebd1d24fa6 100644 --- a/spartan/aztec-network/values/ci-sepolia.yaml +++ b/spartan/aztec-network/values/ci-sepolia.yaml @@ -4,9 +4,6 @@ aztec: realProofs: false l1DeploymentMnemonic: "" numberOfDefaultAccounts: 0 - validatorKeyIndexStart: 0 - proverKeyIndexStart: 3 - botKeyIndexStart: 4 network: setupL2Contracts: false diff --git a/spartan/aztec-network/values/ignition-testnet.yaml b/spartan/aztec-network/values/ignition-testnet.yaml index ce7effe8faa6..c3347571e054 100644 --- a/spartan/aztec-network/values/ignition-testnet.yaml +++ b/spartan/aztec-network/values/ignition-testnet.yaml @@ -4,8 +4,6 @@ telemetry: aztec: realProofs: true numberOfDefaultAccounts: 0 - validatorKeyIndexStart: 0 - proverKeyIndexStart: 3 testAccounts: true bootstrapENRs: "enr:-LO4QDwlKJN0BqMc4hYPsI-MQoR1O7qLVr4TK6DhqGsZT_pPTmg3gS-JD072rKI4vlaR0N4SdeH2gCD09oh-zMVT3JkEhWF6dGVjqDAwLTExMTU1MTExLTAwMDAwMDAwLTAtMmM4ZmM0NjMtMjM3YWFkY2WCaWSCdjSCaXCEI-XzqolzZWNwMjU2azGhA0da3IZGbY1tLdqXgdQKG-SW-Z4D6dvXJBeoXn8EZsCVg3VkcIKd0A,enr:-LO4QPJR493G_BQG1UU0_h-g0TEBnZEJ-zgWYH3YctVAn3GzfM9dWVIO7_TSETXYLy-h34bF6sSoSfpP5O44qsZnp00EhWF6dGVjqDAwLTExMTU1MTExLTAwMDAwMDAwLTAtMmM4ZmM0NjMtMjM3YWFkY2WCaWSCdjSCaXCEIlle64lzZWNwMjU2azGhAwuSF_VE1cRfSc3MvtDZvvaTl2Qo_dJK-Qp7TcnhYWBtg3VkcIKd0A,enr:-LO4QKq488wXvw6vAHToGWJYkxMmKsjQCsFjPs5Pt_MrawlnZ7G-xIfwhkXR1afddf8lFj_RNVZdBfGzHHR262pXNhMEhWF6dGVjqDAwLTExMTU1MTExLTAwMDAwMDAwLTAtMmM4ZmM0NjMtMjM3YWFkY2WCaWSCdjSCaXCEI8VFSYlzZWNwMjU2azGhA2xqOyFaHAARgLAi3dORuPmFHbxgoMDWBZJnnbiatW8jg3VkcIKd0A" contracts: diff --git a/spartan/aztec-network/values/rc-2.yaml b/spartan/aztec-network/values/rc-2.yaml index 6516360ba97e..eb332202ca38 100644 --- a/spartan/aztec-network/values/rc-2.yaml +++ b/spartan/aztec-network/values/rc-2.yaml @@ -5,9 +5,6 @@ aztec: realProofs: true # TODO: Will need to change these as ignition will be using them l1DeploymentMnemonic: "" - validatorKeyIndexStart: 0 - proverKeyIndexStart: 48 - botKeyIndexStart: 49 images: aztec: diff --git a/spartan/aztec-network/values/sepolia-3-validators-with-metrics.yaml b/spartan/aztec-network/values/sepolia-3-validators-with-metrics.yaml index 99803192c18a..6a86713fd5d8 100644 --- a/spartan/aztec-network/values/sepolia-3-validators-with-metrics.yaml +++ b/spartan/aztec-network/values/sepolia-3-validators-with-metrics.yaml @@ -4,9 +4,6 @@ telemetry: aztec: realProofs: false numberOfDefaultAccounts: 0 - validatorKeyIndexStart: 0 - proverKeyIndexStart: 3 - botKeyIndexStart: 4 network: setupL2Contracts: false diff --git a/spartan/aztec-network/values/sepolia-48-validators-with-metrics.yaml b/spartan/aztec-network/values/sepolia-48-validators-with-metrics.yaml index 3b7b4053a693..984c69bf37c7 100644 --- a/spartan/aztec-network/values/sepolia-48-validators-with-metrics.yaml +++ b/spartan/aztec-network/values/sepolia-48-validators-with-metrics.yaml @@ -4,9 +4,6 @@ telemetry: aztec: l1DeploymentMnemonic: "" numberOfDefaultAccounts: 0 - validatorKeyIndexStart: 0 - proverKeyIndexStart: 48 - botKeyIndexStart: 49 network: setupL2Contracts: false diff --git a/spartan/aztec-network/values/sepolia-48-validators-with-proving-and-metrics.yaml b/spartan/aztec-network/values/sepolia-48-validators-with-proving-and-metrics.yaml index dd51254d7cbe..b759c5036367 100644 --- a/spartan/aztec-network/values/sepolia-48-validators-with-proving-and-metrics.yaml +++ b/spartan/aztec-network/values/sepolia-48-validators-with-proving-and-metrics.yaml @@ -5,9 +5,6 @@ aztec: realProofs: true l1DeploymentMnemonic: "" numberOfDefaultAccounts: 0 - validatorKeyIndexStart: 0 - proverKeyIndexStart: 48 - botKeyIndexStart: 49 images: aztec: diff --git a/spartan/scripts/consolidate-sepolia-balances.sh b/spartan/scripts/consolidate-sepolia-balances.sh new file mode 100755 index 000000000000..0a92ea8333b6 --- /dev/null +++ b/spartan/scripts/consolidate-sepolia-balances.sh @@ -0,0 +1,98 @@ +#!/bin/bash + +# Helper script for consolidating balances on Sepolia, that were previously dispersed across multiple accounts. +# The script uses the mnemonic to get the accounts' private keys & calculate which ones were funded from a helm chart yaml. +# Usage: ./consolidate-sepolia-balances.sh +# Environment variables: +# ETHEREUM_HOSTS (must be provided) + +# IMPORTANT NOTE: The script should be the same as the one found in the consolidate-balances.yaml template. +# This standalone is left here for ad-hoc use if needed. + +set -exu + +mnemonic=$1 +funding_address=${2:-"0x33D525f5ac95c2BCf98b644738C7d5673480493A"} +values_file=${3:-"ignition-testnet"} + +XDG_CONFIG_HOME=${XDG_CONFIG_HOME:-"$HOME/.config"} + +ETHEREUM_RPC_URL=$(echo "$ETHEREUM_HOSTS" | cut -d',' -f1) + +# Install cast if needed +if ! command -v cast &>/dev/null; then + curl -L https://foundry.paradigm.xyz | bash + $HOME/.foundry/bin/foundryup && export PATH="$PATH:$HOME/.foundry/bin" || + $XDG_CONFIG_HOME/.foundry/bin/foundryup && export PATH="$PATH:$XDG_CONFIG_HOME/.foundry/bin" +fi + +# Get values from the values file +value_yamls="../aztec-network/values/$values_file ../aztec-network/values.yaml" + +# Get the number of replicas for each service +num_validators=$(./read_value.sh "validator.replicas" $value_yamls) +num_provers=$(./read_value.sh "proverNode.replicas" $value_yamls) + +# Get the key index start values +validator_key_index_start=$(./read_value.sh "aztec.validatorKeyIndexStart" $value_yamls) +prover_key_index_start=$(./read_value.sh "aztec.proverKeyIndexStart" $value_yamls) +bot_key_index_start=$(./read_value.sh "aztec.botKeyIndexStart" $value_yamls) + +# bots might be disabled +bot_enabled=$(./read_value.sh "bot.enabled" $value_yamls) +if [ "$bot_enabled" = "true" ]; then + num_bots=$(./read_value.sh "bot.replicas" $value_yamls) +else + num_bots=0 +fi + +# Build an array of indices to check +declare -a indices_to_check + +# Add validator indices +for ((i = 0; i < num_validators; i++)); do + indices_to_check+=($((validator_key_index_start + i))) +done + +# Add prover indices +for ((i = 0; i < num_provers; i++)); do + indices_to_check+=($((prover_key_index_start + i))) +done + +# Add bot indices if enabled +if [ "$bot_enabled" = "true" ]; then + for ((i = 0; i < num_bots; i++)); do + indices_to_check+=($((bot_key_index_start + i))) + done +fi + +echo "Checking balances for ${#indices_to_check[@]} accounts..." + +# For each index in our list +for i in "${indices_to_check[@]}"; do + # Get address and private key for this index + address=$(cast wallet address --mnemonic "$mnemonic" --mnemonic-index $i) + private_key=$(cast wallet private-key --mnemonic "$mnemonic" --mnemonic-index $i) + + # Get balance + balance=$(cast balance $address --rpc-url "$ETHEREUM_RPC_URL") + + if [ "$balance" != "0" ]; then + gas_price=$(cast gas-price --rpc-url "$ETHEREUM_RPC_URL") + gas_price=$((gas_price * 120 / 100)) # Add 20% to gas price + gas_cost=$((21000 * gas_price)) + + # Calculate amount to send (balance - gas cost) + send_amount=$((balance - gas_cost)) + + if [ "$send_amount" -gt "0" ]; then + echo "Sending $send_amount wei from $address (index $i) to $funding_address" + cast send --private-key "$private_key" --rpc-url "$ETHEREUM_RPC_URL" "$funding_address" \ + --value "$send_amount" --gas-price "$gas_price" --async + else + echo "Balance too low to cover gas costs for $address (index $i)" + fi + else + echo "No balance in $address (index $i)" + fi +done diff --git a/spartan/scripts/deploy_kind.sh b/spartan/scripts/deploy_kind.sh index 4150a900705e..a957ba252590 100755 --- a/spartan/scripts/deploy_kind.sh +++ b/spartan/scripts/deploy_kind.sh @@ -57,7 +57,7 @@ function show_status_until_pxe_ready { show_status_until_pxe_ready & function cleanup { - trap - SIGTERM && kill $(jobs -p) &>/dev/null || true + trap - SIGTERM && kill $(jobs -p) &>/dev/null && rm "$mnemonic_file" || true } trap cleanup SIGINT SIGTERM EXIT @@ -85,7 +85,8 @@ function generate_overrides { if [ "$sepolia_deployment" = "true" ]; then echo "Generating sepolia accounts..." set +x - L1_ACCOUNTS_MNEMONIC=$(./prepare_sepolia_accounts.sh "$values_file" "$mnemonic_file") + ./prepare_sepolia_accounts.sh "$values_file" 1 "$mnemonic_file" + L1_ACCOUNTS_MNEMONIC=$(cat "$mnemonic_file") set -x else echo "Generating devnet config..." @@ -105,19 +106,21 @@ helm_set_args=( # If this is a sepolia run, we need to write some values if [ "$sepolia_deployment" = "true" ]; then set +x + # Escape commas in the EXTERNAL_ETHEREUM_HOSTS value + ESCAPED_HOSTS=$(echo "$EXTERNAL_ETHEREUM_HOSTS" | sed 's/,/\\,/g') helm_set_args+=( - --set ethereum.execution.externalHosts="$EXTERNAL_ETHEREUM_HOSTS" - --set ethereum.beacon.externalHost="$EXTERNAL_ETHEREUM_CONSENSUS_HOST" - --set aztec.l1DeploymentMnemonic="$L1_ACCOUNTS_MNEMONIC" - --set ethereum.deployL1ContractsPrivateKey="$L1_DEPLOYMENT_PRIVATE_KEY" + --set "ethereum.execution.externalHosts=$ESCAPED_HOSTS" + --set "ethereum.beacon.externalHost=$EXTERNAL_ETHEREUM_CONSENSUS_HOST" + --set "aztec.l1DeploymentMnemonic=$L1_ACCOUNTS_MNEMONIC" + --set "ethereum.deployL1ContractsPrivateKey=$L1_DEPLOYMENT_PRIVATE_KEY" ) if [ -n "${EXTERNAL_ETHEREUM_CONSENSUS_HOST_API_KEY:-}" ]; then - helm_set_args+=(--set ethereum.beacon.apiKey="$EXTERNAL_ETHEREUM_CONSENSUS_HOST_API_KEY") + helm_set_args+=(--set "ethereum.beacon.apiKey=$EXTERNAL_ETHEREUM_CONSENSUS_HOST_API_KEY") fi if [ -n "${EXTERNAL_ETHEREUM_CONSENSUS_HOST_API_KEY_HEADER:-}" ]; then - helm_set_args+=(--set ethereum.beacon.apiKeyHeader="$EXTERNAL_ETHEREUM_CONSENSUS_HOST_API_KEY_HEADER") + helm_set_args+=(--set "ethereum.beacon.apiKeyHeader=$EXTERNAL_ETHEREUM_CONSENSUS_HOST_API_KEY_HEADER") fi set -x fi diff --git a/spartan/scripts/prepare_sepolia_accounts.sh b/spartan/scripts/prepare_sepolia_accounts.sh index 419944146e23..e1717ced6ef2 100755 --- a/spartan/scripts/prepare_sepolia_accounts.sh +++ b/spartan/scripts/prepare_sepolia_accounts.sh @@ -5,12 +5,16 @@ set -euo pipefail source $(git rev-parse --show-toplevel)/ci3/source tmp_filename=$(mktemp) +addresses_file=$(mktemp) -# Cleanup function to handle the temp file +# Cleanup function to handle the temp files cleanup() { if [ -f "$tmp_filename" ]; then rm -f "$tmp_filename" fi + if [ -f "$addresses_file" ]; then + rm -f "$addresses_file" + fi } # Set up trap to call cleanup on script exit @@ -21,11 +25,20 @@ eth_amount=${2:-"1"} output_file=${3:-"mnemonic.tmp"} XDG_CONFIG_HOME=${XDG_CONFIG_HOME:-"$HOME/.config"} +# Convert ETH to wei +wei_amount=$(cast to-wei "$eth_amount" ether) + value_yamls="../aztec-network/values/$values_file ../aztec-network/values.yaml" +# Get the number of replicas for each service num_validators=$(./read_value.sh "validator.replicas" $value_yamls) num_provers=$(./read_value.sh "proverNode.replicas" $value_yamls) +# Get the key index start values +validator_key_index_start=$(./read_value.sh "aztec.validatorKeyIndexStart" $value_yamls) +prover_key_index_start=$(./read_value.sh "aztec.proverKeyIndexStart" $value_yamls) +bot_key_index_start=$(./read_value.sh "aztec.botKeyIndexStart" $value_yamls) + # bots might be disabled bot_enabled=$(./read_value.sh "bot.enabled" $value_yamls) if [ "$bot_enabled" = "true" ]; then @@ -34,7 +47,17 @@ else num_bots=0 fi -num_accounts=$((num_validators + num_provers + num_bots)) +# Calculate the highest index needed +validator_max_index=$((validator_key_index_start + num_validators - 1)) +prover_max_index=$((prover_key_index_start + num_provers - 1)) +bot_max_index=$([ "$bot_enabled" = "true" ] && echo $((bot_key_index_start + num_bots - 1)) || echo 0) + +# Find the maximum index needed +max_index=$((validator_max_index > prover_max_index ? validator_max_index : prover_max_index)) +max_index=$((max_index > bot_max_index ? max_index : bot_max_index)) + +# Total number of accounts needed +total_accounts=$((num_validators + num_provers + num_bots)) # Install bc if needed if ! command -v bc &>/dev/null; then @@ -56,35 +79,76 @@ if ! command -v yq &>/dev/null; then chmod +x /usr/local/bin/yq fi -# Create a new mnemonic with the required number of accounts +# Create a new mnemonic echo "Creating mnemonic..." -cast wallet new-mnemonic --accounts "$num_accounts" --json >"$tmp_filename" +cast wallet new-mnemonic --json >"$tmp_filename" MNEMONIC=$(jq -r '.mnemonic' "$tmp_filename") -ADDRESSES=$(jq -r '.accounts[].address' "$tmp_filename") -# Convert ETH to wei -wei_amount=$(cast to-wei "$eth_amount" ether) +echo "MNEMONIC: $MNEMONIC" -# Get current gas price and add 25% buffer -echo "Getting gas price..." -gas_price=$(cast gas-price --rpc-url "$ETHEREUM_HOST") -gas_price=$((gas_price * 125 / 100)) # Add 25% to gas price +# Cast has a limit of 255 accounts per mnemonic command +# We'll need to derive accounts in batches +echo "Deriving $total_accounts accounts from mnemonic..." -# Build 'calls' string in the format: -# [(0xADDR,false,wei_amount,0x),(0xADDR2,false,wei_amount,0x)] +# Function to derive address at a specific index +derive_address() { + local index=$1 + local mnemonic=$2 + cast wallet address --mnemonic "$mnemonic" --mnemonic-index "$index" +} + +# Build an array of indices to fund +declare -a indices_to_fund + +# Add validator indices +for ((i = 0; i < num_validators; i++)); do + indices_to_fund+=($((validator_key_index_start + i))) +done + +# Add prover indices +for ((i = 0; i < num_provers; i++)); do + indices_to_fund+=($((prover_key_index_start + i))) +done + +# Add bot indices if enabled +if [ "$bot_enabled" = "true" ]; then + for ((i = 0; i < num_bots; i++)); do + indices_to_fund+=($((bot_key_index_start + i))) + done +fi + +# Get the addresses to fund calls="[" -for addr in $ADDRESSES; do - calls+="(${addr},false,${wei_amount},0x)," +num_accounts_to_fund=${#indices_to_fund[@]} + +echo "Deriving addresses for $num_accounts_to_fund accounts to fund..." +for index in "${indices_to_fund[@]}"; do + address=$(derive_address "$index" "$MNEMONIC") + calls+="(${address},false,${wei_amount},0x)," done calls=${calls%,} calls+="]" -# Total value = wei_amount * num_accounts -total_value=$(echo "$wei_amount * $num_accounts" | bc) +# Get current gas price and add 25% buffer +echo "Getting gas price..." +gas_price=$(cast gas-price --rpc-url "$ETHEREUM_HOST") +gas_price=$((gas_price * 125 / 100)) # Add 25% to gas price + +# Total value = wei_amount * num_accounts_to_fund +total_value=$(echo "$wei_amount * $num_accounts_to_fund" | bc) + +# Check that we're not sending more than 50% of the funding account balance +funding_address=$(cast wallet address --private-key "$FUNDING_PRIVATE_KEY") +funding_balance=$(cast balance --rpc-url "$ETHEREUM_HOST" "$funding_address") +half_balance=$(echo "$funding_balance / 2" | bc) +if (($(echo "$total_value > $half_balance" | bc -l))); then + echo "Error: Total value of this tx exceeds 50% of funding account balance" + exit 1 +fi multicall_address="0xcA11bde05977b3631167028862bE2a173976CA11" # Sepolia Multicall3 contract -echo "Sending transaction..." +echo "Sending transaction to fund $num_accounts_to_fund accounts..." tx_hash=$(cast send "$multicall_address" \ "aggregate3Value((address,bool,uint256,bytes)[])" \ "$calls" \ @@ -93,7 +157,13 @@ tx_hash=$(cast send "$multicall_address" \ --rpc-url "$ETHEREUM_HOST" \ --json --gas-price "$gas_price") -echo "Sent ${wei_amount} wei to ${num_accounts} addresses in tx $tx_hash" +echo "Sent ${wei_amount} wei to ${num_accounts_to_fund} addresses in tx $tx_hash" +echo "Funded accounts for:" +echo "- $num_validators validators (starting at index $validator_key_index_start)" +echo "- $num_provers provers (starting at index $prover_key_index_start)" +if [ "$bot_enabled" = "true" ]; then + echo "- $num_bots bots (starting at index $bot_key_index_start)" +fi # Write mnemonic to output file echo "$MNEMONIC" >"$output_file" diff --git a/spartan/scripts/test_kind.sh b/spartan/scripts/test_kind.sh index 6b737489f010..705aec4b735f 100755 --- a/spartan/scripts/test_kind.sh +++ b/spartan/scripts/test_kind.sh @@ -57,6 +57,8 @@ fi # If fresh_install is true, delete the namespace if [ "$fresh_install" = "true" ]; then echo "Deleting existing namespace due to FRESH_INSTALL=true" + # Run helm uninstall first to ensure post-delete hooks are run + helm uninstall "$helm_instance" -n "$namespace" 2>/dev/null || true kubectl delete namespace "$namespace" --ignore-not-found=true --wait=true --now --timeout=10m &>/dev/null || true fi @@ -69,6 +71,8 @@ function cleanup { if [ "$cleanup_cluster" = "true" ]; then kind delete cluster || true elif [ "$fresh_install" = "true" ]; then + # Run helm uninstall first to ensure post-delete hooks are run + helm uninstall "$helm_instance" -n "$namespace" 2>/dev/null || true kubectl delete namespace "$namespace" --ignore-not-found=true --wait=true --now --timeout=10m &>/dev/null || true fi }