{# T28 admin dashboard — Tailwind redesign. Extends the new admin layout. #}
{# Data shape (collect_all_stats) is unchanged; this template only #}
{# re-skins the eight KPI cards into a 12-column grid. #}
{% extends "admin_layout.html" %}
{% block page_title %}Admin dashboard{% endblock %}
{% block breadcrumb %}
Admin
/
Dashboard
{% endblock %}
{% macro stat_tile(label, value) -%}
{# ===================== Volume ===================== #}
{{ card_heading('Scan Volume') }}
{{ stat_tile('Today', volume.today) }}
{{ stat_tile('Last 7d', volume.last_7_days) }}
{{ stat_tile('Last 30d', volume.last_30_days) }}
{# ===================== Outcomes ===================== #}
{{ card_heading('Outcomes') }}
{{ '%.1f'|format(outcome.success_rate * 100) }}%
success rate
{{ outcome.errored_count }} errored / {{ outcome.total_scans }} total
Top error reasons
{% if not outcome.top_error_reasons %}
{{ empty_state('No errors recorded.') }}
{% else %}
| Reason |
Count |
{% for row in outcome.top_error_reasons %}
| {{ row.reason }} |
{{ row.count }} |
{% endfor %}
{% endif %}
{# ===================== Cost ===================== #}
{{ card_heading('Cost') }}
{{ stat_tile('Total', '$' ~ '%.2f'|format(cost.total_usd)) }}
{{ stat_tile('Today', '$' ~ '%.2f'|format(cost.today_usd)) }}
{{ stat_tile('Max / scan', '$' ~ '%.4f'|format(cost.max_per_scan_usd)) }}
{{ stat_tile('Avg / scan', '$' ~ '%.4f'|format(cost.avg_per_scan_usd)) }}
Prompt cost trend (30 days)
{% if not cost.prompt_cost_trend %}
{{ empty_state('No LLM cost data in the last 30 days.') }}
{% else %}
{% endif %}
{# ===================== Users ===================== #}
{{ card_heading('Users') }}
{{ stat_tile('Total users', users.total_users) }}
{{ stat_tile('Active (30d)', users.active_30d) }}
Top 5 spenders
{% if not users.top_5_spenders %}
{{ empty_state('No spend recorded yet.') }}
{% else %}
| User |
Scans |
Spend |
{% for row in users.top_5_spenders %}
{{ row.label }} |
{{ row.scan_count }} |
${{ '%.4f'|format(row.total_usd) }} |
{% endfor %}
{% endif %}
{# ===================== Sandbox experiments ===================== #}
{{ card_heading('Sandbox experiments') }}
{{ stat_tile('Total', '$' ~ '%.2f'|format(experiment_cost.total_usd)) }}
{{ stat_tile('Today', '$' ~ '%.2f'|format(experiment_cost.today_usd)) }}
{{ stat_tile('Runs', experiment_cost.experiment_count) }}
Top experimenters
{% if not experiment_cost.top_experimenters %}
{{ empty_state('No sandbox spend yet.') }}
{% else %}
| Admin |
Runs |
Spend |
{% for row in experiment_cost.top_experimenters %}
{{ row.label }} |
{{ row.experiment_count }} |
${{ '%.4f'|format(row.total_usd) }} |
{% endfor %}
{% endif %}
All experiments →
{# ===================== LLM reliability ===================== #}
{{ card_heading('LLM reliability') }}
{% if not llm_reliability.per_prompt %}
{{ empty_state('No LLM calls recorded yet.') }}
{% else %}
| Prompt |
OK |
Fail |
Retries |
p95 (ms) |
{% for row in llm_reliability.per_prompt %}
{{ row.prompt_name }} |
{{ row.success_count }} |
{{ row.failure_count }} |
{{ row.retry_count }} |
{{ '%.0f'|format(row.p95_latency_ms) }} |
{% endfor %}
{% endif %}
{# ===================== Prompt cost ===================== #}
{{ card_heading('Prompt cost') }}
{% if not prompt_cost.per_prompt %}
{{ empty_state('No LLM cost data recorded yet.') }}
{% else %}
| Prompt |
Calls |
Avg |
Max |
Min |
{% for row in prompt_cost.per_prompt %}
{{ row.prompt_name }} |
{{ row.call_count }} |
${{ '%.4f'|format(row.avg_usd) }} |
${{ '%.4f'|format(row.max_usd) }} |
${{ '%.4f'|format(row.min_usd) }} |
{% endfor %}
{% endif %}
{# ===================== Top domains ===================== #}
{{ card_heading('Scan type — top domains') }}
{% if not top_domains %}
{{ empty_state('No scans yet.') }}
{% else %}
| Domain |
Scans |
{% for row in top_domains %}
{{ row.domain }} |
{{ row.count }} |
{% endfor %}
{% endif %}
{# ===================== Top templates ===================== #}
{{ card_heading('Template — top scanned') }}
{% if not top_templates %}
{{ empty_state('No scans yet.') }}
{% else %}
| Template |
Scans |
{% for row in top_templates %}
{{ row.template }} |
{{ row.count }} |
{% endfor %}
{% endif %}
{% endblock %}
{% block scripts %}
{% if cost.prompt_cost_trend %}
{% endif %}
{% endblock %}