#!/bin/bash

# Runs the testsuite X times and collects the mem spent for each run, 
# at the end, it summarises the results (max, median, avg).
# It's best to run just a single test using `.only` so it's quick.
#
# Usage: ./bench.sh <test-file> <benchmark-name> <runs>
# Example: ./bench.sh interest-collection.test.ts "Interest Collection - Batch Collect 13 CDPs" 20

if [ "$#" -ne 3 ]; then
  echo "Usage: $0 <test-file> <benchmark-name> <runs>"
  echo "Example: $0 interest-collection.test.ts \"Interest Collection - Batch Collect 13 CDPs\" 20"
  exit 1
fi

test_file="$1"
benchmark_name="$2"
runs="$3"

if ! [[ "$runs" =~ ^[0-9]+$ ]] || [ "$runs" -lt 1 ]; then
  echo "Error: <runs> must be a positive integer"
  exit 1
fi

total=0
values=()

for i in $(seq 1 $runs); do
  echo -n "Run $i/$runs... "
  output=$(pnpm test "$test_file" 2>&1)
  mem=$(echo "$output" | grep "$benchmark_name" | grep -oP "'\d+\.\d+%'" | head -1 | tr -d "'%")

  if [ -z "$mem" ]; then
    echo "ERROR: benchmark '$benchmark_name' not found in output — aborting"
    exit 1
  fi

  echo "Memory: ${mem}%"
  values+=("$mem")
  total=$(echo "$total + $mem" | bc)
done

sorted=($(printf '%s\n' "${values[@]}" | sort -n))

avg=$(echo "scale=3; $total / $runs" | bc)
min=${sorted[0]}
max=${sorted[$runs-1]}

mid=$(($runs / 2))
if (( $runs % 2 == 0 )); then
  median=$(echo "scale=3; (${sorted[$mid-1]} + ${sorted[$mid]}) / 2" | bc)
else
  median=${sorted[$mid]}
fi

echo ""
echo "=== Benchmark: $benchmark_name ==="
echo "=== Test file: $test_file | Runs: $runs ==="
echo "Average : ${avg}%"
echo "Minimum : ${min}%"
echo "Maximum : ${max}%"
echo "Median  : ${median}%"