import { useState, useEffect, useCallback } from 'react' import { Bot, Clock, RefreshCw } from 'lucide-react' import { getLatestInsight, generateInsight } from '../api' import { formatAge, renderContent } from '../lib/aiInsight' import type { AIInsight } from '../types' const REFRESH_MS = 5 * 60_000 export default function Dashboard() { const [insight, setInsight] = useState(null) const [loading, setLoading] = useState(true) const [error, setError] = useState(null) const [generating, setGenerating] = useState(false) const [genError, setGenError] = useState(null) const load = useCallback(() => { getLatestInsight() .then(setInsight) .catch(e => setError(e instanceof Error ? e.message : 'Failed to load insight')) .finally(() => setLoading(false)) }, []) useEffect(() => { load() const id = setInterval(load, REFRESH_MS) return () => clearInterval(id) }, [load]) const handleGenerate = async () => { setGenerating(true) setGenError(null) try { await generateInsight() load() } catch (e) { setGenError(e instanceof Error ? e.message : 'Failed to generate insight') } finally { setGenerating(false) } } return (

Dashboard

{genError &&
{genError}
}
AI Insight
{insight && ( {formatAge(insight.generated_at)} {insight.model && ( {insight.model} )} )}
{loading &&
Loading…
} {!loading && error &&
{error}
} {!loading && !error && !insight && (
No insight generated yet. Click Generate Now to produce a summary.
)} {!loading && !error && insight && (
{renderContent(insight.content)}
{(insight.input_tokens || insight.output_tokens) && (
{insight.input_tokens}↑ / {insight.output_tokens}↓ tokens · {insight.triggered_by}
)}
)}
) }