#!/bin/bash # Price Feed Keeper Service (Bash version) # Simple bash-based keeper that calls the keeper contract periodically set -e SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)" cd "$PROJECT_ROOT" source "$PROJECT_ROOT/scripts/load-env.sh" >/dev/null 2>&1 || true # Load environment variables if [ -f .env ]; then source .env fi # Configuration RPC_URL="${RPC_URL_138:-http://localhost:8545}" KEEPER_ADDRESS="${PRICE_FEED_KEEPER_ADDRESS}" UPDATE_INTERVAL="${UPDATE_INTERVAL:-6}" # seconds (PMM mesh / peg tick cadence) MAX_RETRIES=3 # Colors for output RED='\033[0;31m' GREEN='\033[0;32m' YELLOW='\033[1;33m' NC='\033[0m' # No Color # Statistics UPDATE_COUNT=0 ERROR_COUNT=0 # Function to log messages log() { echo -e "[$(date +'%Y-%m-%d %H:%M:%S')] $1" } # Function to check if upkeep is needed check_upkeep() { forge script script/reserve/CheckUpkeep.s.sol:CheckUpkeep \ --rpc-url "$RPC_URL" \ --silent 2>/dev/null | grep -E "(needsUpdate|assets)" || echo "false" } # Function to perform upkeep perform_upkeep() { log "${YELLOW}Performing upkeep...${NC}" local retries=0 local success=false while [ $retries -lt $MAX_RETRIES ] && [ "$success" = false ]; do if forge script script/reserve/PerformUpkeep.s.sol:PerformUpkeep \ --rpc-url "$RPC_URL" \ --broadcast \ --silent 2>/dev/null; then success=true UPDATE_COUNT=$((UPDATE_COUNT + 1)) log "${GREEN}✓ Upkeep successful${NC}" else retries=$((retries + 1)) if [ $retries -lt $MAX_RETRIES ]; then log "${YELLOW}Retry $retries/$MAX_RETRIES...${NC}" sleep 5 else ERROR_COUNT=$((ERROR_COUNT + 1)) log "${RED}✗ Upkeep failed after $MAX_RETRIES retries${NC}" fi fi done } # Function to stop keeper stop_keeper() { log "\nStopping keeper service..." log "\n=== Statistics ===" log "Total Updates: $UPDATE_COUNT" log "Total Errors: $ERROR_COUNT" if [ $UPDATE_COUNT -gt 0 ]; then local success_rate=$(echo "scale=2; ($UPDATE_COUNT * 100) / ($UPDATE_COUNT + $ERROR_COUNT)" | bc) log "Success Rate: ${success_rate}%" fi exit 0 } # Trap signals for graceful shutdown trap stop_keeper SIGINT SIGTERM # Main loop main() { log "${GREEN}=== Price Feed Keeper Service ===${NC}" log "RPC URL: $RPC_URL" log "Keeper Address: $KEEPER_ADDRESS" log "Update Interval: $UPDATE_INTERVAL seconds" log "" log "Keeper service started. Press Ctrl+C to stop." log "" while true; do # Check if upkeep is needed if check_upkeep | grep -q "true"; then perform_upkeep else log "No updates needed" fi # Wait for next interval sleep "$UPDATE_INTERVAL" done } # Run main function main