#!/bin/sh
# Factory Dashboard - Aggregated mesh status
# CGI endpoint for SecuBox Factory

echo "Content-Type: application/json"
echo "Access-Control-Allow-Origin: *"
echo "Access-Control-Allow-Methods: GET, OPTIONS"
echo ""

# Handle CORS preflight
if [ "$REQUEST_METHOD" = "OPTIONS" ]; then
	exit 0
fi

# Load factory library
. /usr/lib/secubox/factory.sh 2>/dev/null

# Get local node status
get_local_status() {
	if [ -x /usr/sbin/secubox-p2p ]; then
		/usr/sbin/secubox-p2p status 2>/dev/null
	else
		echo '{"error":"p2p_unavailable"}'
	fi
}

# Get services status
get_services_status() {
	local running=0
	local total=0

	for init_script in /etc/init.d/*; do
		[ -x "$init_script" ] || continue
		local svc_name=$(basename "$init_script")

		# Skip system services
		case "$svc_name" in
			boot|done|rcS|rc.local|umount|sysfixtime|sysntpd|gpio_switch) continue ;;
		esac

		total=$((total + 1))
		if pgrep "$svc_name" >/dev/null 2>&1; then
			running=$((running + 1))
		fi
	done

	echo "{\"running\":$running,\"total\":$total}"
}

# Get system stats
get_system_stats() {
	local uptime_val=$(cat /proc/uptime 2>/dev/null | cut -d' ' -f1)
	local load=$(cat /proc/loadavg 2>/dev/null | cut -d' ' -f1)
	local mem_info=$(cat /proc/meminfo 2>/dev/null)
	local mem_total=$(echo "$mem_info" | grep MemTotal | awk '{print $2}')
	local mem_free=$(echo "$mem_info" | grep MemAvailable | awk '{print $2}')
	[ -z "$mem_free" ] && mem_free=$(echo "$mem_info" | grep MemFree | awk '{print $2}')

	local mem_used=0
	local mem_pct=0
	if [ -n "$mem_total" ] && [ "$mem_total" -gt 0 ]; then
		mem_used=$((mem_total - mem_free))
		mem_pct=$((mem_used * 100 / mem_total))
	fi

	echo "{\"uptime\":${uptime_val:-0},\"load\":\"${load:-0}\",\"mem_used_kb\":$mem_used,\"mem_total_kb\":${mem_total:-0},\"mem_pct\":$mem_pct}"
}

# Get peer statuses
get_peer_statuses() {
	local peers_file="/tmp/secubox-p2p-peers.json"
	local result="["
	local first=1

	if [ -f "$peers_file" ]; then
		# Parse each peer
		local peers=$(jsonfilter -i "$peers_file" -e '@.peers[*]' 2>/dev/null)
		local count=$(jsonfilter -i "$peers_file" -e '@.peers[*]' 2>/dev/null | wc -l)
		local i=0

		while [ $i -lt $count ]; do
			local addr=$(jsonfilter -i "$peers_file" -e "@.peers[$i].address" 2>/dev/null)
			local name=$(jsonfilter -i "$peers_file" -e "@.peers[$i].name" 2>/dev/null)
			local is_local=$(jsonfilter -i "$peers_file" -e "@.peers[$i].is_local" 2>/dev/null)

			if [ -n "$addr" ] && [ "$is_local" != "true" ]; then
				# Try to get peer status (with timeout)
				local peer_status=$(curl -s --connect-timeout 2 "http://$addr:7331/api/status" 2>/dev/null)
				local status="offline"
				local peer_merkle=""

				if [ -n "$peer_status" ] && echo "$peer_status" | grep -q "node_id"; then
					status="online"
					# Try to get peer's merkle root
					peer_merkle=$(curl -s --connect-timeout 1 "http://$addr:7331/api/factory/snapshot" 2>/dev/null | jsonfilter -e '@.merkle_root' 2>/dev/null)
				fi

				[ $first -eq 0 ] && result="$result,"
				first=0
				result="$result{\"address\":\"$addr\",\"name\":\"$name\",\"status\":\"$status\",\"merkle_root\":\"${peer_merkle:-}\"}"
			fi
			i=$((i + 1))
		done
	fi

	result="$result]"
	echo "$result"
}

# Main response
local_status=$(get_local_status)
local_merkle=$(merkle_config 2>/dev/null || echo "")
snapshot=$(get_snapshot 2>/dev/null | tr '\n' ' ' | tr '\t' ' ')
services=$(get_services_status)
system=$(get_system_stats)
peers=$(get_peer_statuses)
pending=$(pending_count 2>/dev/null || echo "0")
fingerprint=$(factory_fingerprint 2>/dev/null || echo "")

# Build response
cat << EOF
{
	"local": $local_status,
	"merkle_root": "$local_merkle",
	"snapshot": $snapshot,
	"services": $services,
	"system": $system,
	"peers": $peers,
	"pending_ops": $pending,
	"fingerprint": "$fingerprint"
}
EOF
