{% extends "base.html" %}

{% block title %}Watcher Manager — Admin{% endblock %}

{% block content %}
<div class="mb-6">
    <div class="flex items-center gap-3">
        <h1 class="text-3xl font-bold text-gray-900 dark:text-white">Watcher Manager</h1>
        <span class="px-2 py-0.5 text-xs font-semibold bg-orange-100 text-orange-700 dark:bg-orange-900 dark:text-orange-300 rounded-full">Admin</span>
    </div>
    <p class="text-gray-500 dark:text-gray-400 mt-1 text-sm">
        Monitor and manage field watcher agents. Data updates on each heartbeat received.
    </p>
</div>

<!-- Agent cards -->
<div id="agent-list" class="space-y-4">

{% if not agents %}
<div class="bg-white dark:bg-slate-800 rounded-xl shadow p-8 text-center">
    <svg class="w-12 h-12 mx-auto text-gray-300 dark:text-gray-600 mb-3" fill="none" stroke="currentColor" viewBox="0 0 24 24">
        <path stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5" d="M9.75 17L9 20l-1 1h8l-1-1-.75-3M3 13h18M5 17h14a2 2 0 002-2V5a2 2 0 00-2-2H5a2 2 0 00-2 2v10a2 2 0 002 2z"/>
    </svg>
    <p class="text-gray-500 dark:text-gray-400">No watcher agents have reported in yet.</p>
    <p class="text-sm text-gray-400 dark:text-gray-500 mt-1">Once a watcher sends its first heartbeat it will appear here.</p>
</div>
{% endif %}

{% for agent in agents %}
<div class="bg-white dark:bg-slate-800 rounded-xl shadow-lg overflow-hidden" id="agent-{{ agent.id | replace(' ', '-') }}">

    <!-- Card header -->
    <div class="flex items-center justify-between px-6 py-4 border-b border-gray-100 dark:border-slate-700">
        <div class="flex items-center gap-3">
            <!-- Status dot -->
            {% if agent.status == 'ok' %}
            <span class="status-dot inline-block w-3 h-3 rounded-full bg-green-500 flex-shrink-0"></span>
            {% elif agent.status == 'pending' %}
            <span class="status-dot inline-block w-3 h-3 rounded-full bg-yellow-400 flex-shrink-0"></span>
            {% elif agent.status in ('missing', 'error') %}
            <span class="status-dot inline-block w-3 h-3 rounded-full bg-red-500 flex-shrink-0"></span>
            {% else %}
            <span class="status-dot inline-block w-3 h-3 rounded-full bg-gray-400 flex-shrink-0"></span>
            {% endif %}

            <div>
                <h2 class="text-lg font-semibold text-gray-900 dark:text-white">{{ agent.id }}</h2>
                <div class="flex items-center gap-3 text-xs text-gray-500 dark:text-gray-400 mt-0.5">
                    <span>{{ agent.source_type }}</span>
                    {% if agent.version %}
                    <span class="bg-gray-100 dark:bg-slate-700 px-1.5 py-0.5 rounded font-mono">v{{ agent.version }}</span>
                    {% endif %}
                    {% if agent.ip_address %}
                    <span>{{ agent.ip_address }}</span>
                    {% endif %}
                </div>
            </div>
        </div>

        <div class="flex items-center gap-3">
            <!-- Status badge -->
            {% if agent.status == 'ok' %}
            <span class="status-badge px-2.5 py-1 text-xs font-semibold rounded-full bg-green-100 text-green-700 dark:bg-green-900 dark:text-green-300">OK</span>
            {% elif agent.status == 'pending' %}
            <span class="status-badge px-2.5 py-1 text-xs font-semibold rounded-full bg-yellow-100 text-yellow-700 dark:bg-yellow-900 dark:text-yellow-300">Pending</span>
            {% elif agent.status == 'missing' %}
            <span class="status-badge px-2.5 py-1 text-xs font-semibold rounded-full bg-red-100 text-red-700 dark:bg-red-900 dark:text-red-300">Missing</span>
            {% elif agent.status == 'error' %}
            <span class="status-badge px-2.5 py-1 text-xs font-semibold rounded-full bg-red-100 text-red-700 dark:bg-red-900 dark:text-red-300">Error</span>
            {% else %}
            <span class="status-badge px-2.5 py-1 text-xs font-semibold rounded-full bg-gray-100 text-gray-600 dark:bg-slate-700 dark:text-gray-400">Unknown</span>
            {% endif %}

            <!-- Trigger Update button -->
            <button
                onclick="triggerUpdate('{{ agent.id }}')"
                class="px-3 py-1.5 text-xs font-medium bg-seismo-orange hover:bg-orange-600 text-white rounded-lg transition-colors"
                id="btn-update-{{ agent.id | replace(' ', '-') }}"
            >
                Trigger Update
            </button>
        </div>
    </div>

    <!-- Meta row -->
    <div class="px-6 py-3 bg-gray-50 dark:bg-slate-800 border-b border-gray-100 dark:border-slate-700 flex flex-wrap gap-6 text-sm">
        <div>
            <span class="text-gray-500 dark:text-gray-400">Last seen</span>
            <span class="last-seen-value ml-2 font-medium text-gray-800 dark:text-gray-200">
                {% if agent.last_seen %}
                    {{ agent.last_seen }}
                    {% if agent.age_minutes is not none %}
                    <span class="text-gray-400 dark:text-gray-500 font-normal">({{ agent.age_minutes }}m ago)</span>
                    {% endif %}
                {% else %}
                    Never
                {% endif %}
            </span>
        </div>
        <div class="update-pending-indicator flex items-center gap-1.5 text-yellow-600 dark:text-yellow-400 {% if not agent.update_pending %}hidden{% endif %}">
            <svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
                <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15"/>
            </svg>
            <span class="text-xs font-semibold">Update pending — will apply on next heartbeat</span>
        </div>
    </div>

    <!-- Log tail -->
    {% if agent.log_tail %}
    <div class="px-6 py-4">
        <div class="flex items-center justify-between mb-2">
            <span class="text-xs font-semibold text-gray-500 dark:text-gray-400 uppercase tracking-wide">Log Tail</span>
            <div class="flex items-center gap-3">
                <button onclick="expandLog('{{ agent.id | replace(' ', '-') }}')" id="expand-{{ agent.id | replace(' ', '-') }}" class="text-xs text-gray-400 hover:text-gray-600 dark:hover:text-gray-200">
                    Expand
                </button>
                <button onclick="toggleLog('{{ agent.id | replace(' ', '-') }}')" class="text-xs text-gray-400 hover:text-gray-600 dark:hover:text-gray-200">
                    Toggle
                </button>
            </div>
        </div>
        <pre id="log-{{ agent.id | replace(' ', '-') }}" class="text-xs font-mono bg-gray-900 text-green-400 rounded-lg p-3 overflow-x-auto max-h-96 overflow-y-auto leading-relaxed hidden">{{ agent.log_tail | log_tail_display }}</pre>
    </div>
    {% else %}
    <div class="px-6 py-4 text-xs text-gray-400 dark:text-gray-500 italic">No log data received yet.</div>
    {% endif %}

</div>
{% endfor %}

</div>

<!-- Auto-refresh every 30s -->
<div class="mt-6 text-xs text-gray-400 dark:text-gray-600 text-center">
    Auto-refreshes every 30 seconds &mdash; or <a href="/admin/watchers" class="underline hover:text-gray-600 dark:hover:text-gray-400">refresh now</a>
</div>

<script>
function triggerUpdate(agentId) {
    if (!confirm('Trigger update for ' + agentId + '?\n\nThe watcher will self-update on its next heartbeat cycle.')) return;

    const safeId = agentId.replace(/ /g, '-');
    const btn = document.getElementById('btn-update-' + safeId);
    btn.disabled = true;
    btn.textContent = 'Sending...';

    fetch('/api/admin/watchers/' + encodeURIComponent(agentId) + '/trigger-update', {
        method: 'POST',
        headers: {'Content-Type': 'application/json'},
        body: JSON.stringify({})
    })
    .then(r => r.json())
    .then(data => {
        if (data.ok) {
            btn.textContent = 'Update Queued';
            btn.classList.remove('bg-seismo-orange', 'hover:bg-orange-600');
            btn.classList.add('bg-green-600');
            // Show the pending indicator immediately without a reload
            const card = document.getElementById('agent-' + safeId);
            if (card) {
                const indicator = card.querySelector('.update-pending-indicator');
                if (indicator) indicator.classList.remove('hidden');
            }
        } else {
            btn.textContent = 'Error';
            btn.classList.add('bg-red-600');
            btn.disabled = false;
        }
    })
    .catch(() => {
        btn.textContent = 'Failed';
        btn.classList.add('bg-red-600');
        btn.disabled = false;
    });
}

function toggleLog(agentId) {
    const el = document.getElementById('log-' + agentId);
    if (el) el.classList.toggle('hidden');
}

function expandLog(agentId) {
    const el = document.getElementById('log-' + agentId);
    const btn = document.getElementById('expand-' + agentId);
    if (!el) return;
    el.classList.remove('hidden');
    if (el.classList.contains('max-h-96')) {
        el.classList.remove('max-h-96');
        el.style.maxHeight = 'none';
        if (btn) btn.textContent = 'Collapse';
    } else {
        el.classList.add('max-h-96');
        el.style.maxHeight = '';
        if (btn) btn.textContent = 'Expand';
    }
}

// Status colors for dot and badge by status value
const STATUS_DOT = {
    ok:      'bg-green-500',
    pending: 'bg-yellow-400',
    missing: 'bg-red-500',
    error:   'bg-red-500',
};
const STATUS_BADGE_CLASSES = {
    ok:      'bg-green-100 text-green-700 dark:bg-green-900 dark:text-green-300',
    pending: 'bg-yellow-100 text-yellow-700 dark:bg-yellow-900 dark:text-yellow-300',
    missing: 'bg-red-100 text-red-700 dark:bg-red-900 dark:text-red-300',
    error:   'bg-red-100 text-red-700 dark:bg-red-900 dark:text-red-300',
};
const STATUS_BADGE_DEFAULT = 'bg-gray-100 text-gray-600 dark:bg-slate-700 dark:text-gray-400';
const DOT_COLORS = ['bg-green-500', 'bg-yellow-400', 'bg-red-500', 'bg-gray-400'];
const BADGE_COLORS = [
    'bg-green-100', 'text-green-700', 'dark:bg-green-900', 'dark:text-green-300',
    'bg-yellow-100', 'text-yellow-700', 'dark:bg-yellow-900', 'dark:text-yellow-300',
    'bg-red-100', 'text-red-700', 'dark:bg-red-900', 'dark:text-red-300',
    'bg-gray-100', 'text-gray-600', 'dark:bg-slate-700', 'dark:text-gray-400',
];

function patchAgent(card, agent) {
    // Status dot
    const dot = card.querySelector('.status-dot');
    if (dot) {
        dot.classList.remove(...DOT_COLORS);
        dot.classList.add(STATUS_DOT[agent.status] || 'bg-gray-400');
    }

    // Status badge
    const badge = card.querySelector('.status-badge');
    if (badge) {
        badge.classList.remove(...BADGE_COLORS);
        const label = agent.status ? agent.status.charAt(0).toUpperCase() + agent.status.slice(1) : 'Unknown';
        badge.textContent = label === 'Ok' ? 'OK' : label;
        const cls = STATUS_BADGE_CLASSES[agent.status] || STATUS_BADGE_DEFAULT;
        badge.classList.add(...cls.split(' '));
    }

    // Last seen / age
    const lastSeen = card.querySelector('.last-seen-value');
    if (lastSeen) {
        if (agent.last_seen) {
            const age = agent.age_minutes != null
                ? ` <span class="text-gray-400 dark:text-gray-500 font-normal">(${agent.age_minutes}m ago)</span>`
                : '';
            lastSeen.innerHTML = agent.last_seen + age;
        } else {
            lastSeen.textContent = 'Never';
        }
    }

    // Update pending indicator
    const indicator = card.querySelector('.update-pending-indicator');
    if (indicator) {
        indicator.classList.toggle('hidden', !agent.update_pending);
    }
}

function liveRefresh() {
    fetch('/api/admin/watchers')
        .then(r => r.json())
        .then(agents => {
            agents.forEach(agent => {
                const safeId = agent.id.replace(/ /g, '-');
                const card = document.getElementById('agent-' + safeId);
                if (card) patchAgent(card, agent);
            });
        })
        .catch(() => {}); // silently ignore fetch errors
}

setInterval(liveRefresh, 30000);
</script>
{% endblock %}
