added basic analytics
All checks were successful
Deploy / Check & Build (push) Successful in 1m14s
Deploy / Deploy to Production (push) Successful in 1m10s

This commit is contained in:
RaineAllDay
2026-03-18 05:32:50 -06:00
parent e6d6cc01da
commit 272ab85b62
4 changed files with 166 additions and 18 deletions

View File

@@ -188,6 +188,8 @@
return new Date(iso).toLocaleString();
}
$: viewMax = Math.max(...(data.views?.chart ?? []).map(d => d.visitors), 1);
const reasonLabels = {
'incorrect-data': 'Incorrect data',
'duplicate': 'Duplicate',
@@ -218,6 +220,63 @@
{/each}
</div>
<!-- Visitor stats -->
<div class="panel" style="margin-bottom:24px; overflow:hidden;">
<div style="padding:14px 18px; border-bottom:1px solid var(--border); display:flex; align-items:center; gap:12px;">
<div style="font-family:'Barlow Condensed',sans-serif; font-weight:700; font-size:15px;
letter-spacing:0.06em; text-transform:uppercase; color:var(--text);">
Unique Visitors
</div>
<div style="font-family:'DM Mono',monospace; font-size:11px; color:var(--text3);">
hashed IPs · 6h dedup window · 90 day retention
</div>
</div>
<div style="padding:16px 20px; display:flex; align-items:stretch; gap:24px; flex-wrap:wrap;">
<!-- Counters -->
<div style="display:flex; gap:24px; flex-shrink:0;">
{#each [
{ label: 'Today', value: data.views.todayCount, color: 'var(--amber)' },
{ label: 'Yesterday', value: data.views.yesterdayCount, color: 'var(--text2)' },
{ label: '7-day', value: data.views.weekTotal, color: 'var(--cyan)' },
] as v}
<div>
<div class="label" style="margin-bottom:4px;">{v.label}</div>
<div style="font-family:'DM Mono',monospace; font-size:28px; font-weight:500;
color:{v.color}; text-shadow:0 0 12px {v.color}40; line-height:1;">
{v.value}
</div>
</div>
{/each}
</div>
<!-- Sparkline -->
<div style="flex:1; min-width:200px; display:flex; flex-direction:column; justify-content:flex-end;">
<div style="display:flex; align-items:flex-end; gap:3px; height:48px;">
{#each data.views.chart as day, i}
{@const pct = (day.visitors / viewMax) * 100}
{@const isToday = i === data.views.chart.length - 1}
<div style="flex:1; display:flex; flex-direction:column; align-items:center; gap:3px; height:100%;">
<div style="width:100%; border-radius:2px 2px 0 0;
background:{isToday ? 'var(--amber)' : 'var(--border2)'};
box-shadow:{isToday ? '0 0 8px rgba(232,147,10,0.4)' : 'none'};
height:{Math.max(pct, 4)}%;
margin-top:auto;"
title="{day.date}: {day.visitors} visitor{day.visitors !== 1 ? 's' : ''}">
</div>
</div>
{/each}
</div>
<div style="display:flex; justify-content:space-between; margin-top:4px;
font-family:'DM Mono',monospace; font-size:9px; color:var(--text3);">
<span>{data.views.chart[0]?.date.slice(5)}</span>
<span>today</span>
</div>
</div>
</div>
</div>
<!-- Messages section -->
<div class="panel" style="margin-bottom:24px; overflow:hidden;">
<div style="padding:14px 18px; border-bottom:1px solid var(--border);