fiemwl / src /app /docs /components /DocsPageAnalytics.tsx
automindy's picture
Upload 1980 files
6111b2b verified
Raw
History Blame Contribute Delete
2.24 kB
"use client";
import { useEffect, useCallback, useRef } from "react";
interface PageAnalyticsProps {
slug: string;
title: string;
section: string;
}
const STORAGE_KEY = "omniroute_docs_analytics";
const MAX_EVENTS = 200;
interface AnalyticsEvent {
slug: string;
title: string;
section: string;
timestamp: number;
referrer: string;
}
function getEvents(): AnalyticsEvent[] {
try {
const raw = localStorage.getItem(STORAGE_KEY);
if (!raw) return [];
return JSON.parse(raw);
} catch {
return [];
}
}
function pruneEvents(events: AnalyticsEvent[]): AnalyticsEvent[] {
return events.slice(-MAX_EVENTS);
}
export function DocsPageAnalytics({ slug, title, section }: PageAnalyticsProps) {
const trackedRef = useRef(false);
const trackPageView = useCallback(() => {
if (trackedRef.current) return;
trackedRef.current = true;
try {
const events = getEvents();
events.push({
slug,
title,
section,
timestamp: Date.now(),
referrer: typeof document !== "undefined" ? document.referrer : "",
});
localStorage.setItem(STORAGE_KEY, JSON.stringify(pruneEvents(events)));
} catch {
// localStorage unavailable — silent fail
}
}, [slug, title, section]);
useEffect(() => {
trackPageView();
}, [trackPageView]);
return null; // invisible tracking component
}
export function getPopularPages(
limit = 5
): { slug: string; title: string; section: string; views: number }[] {
if (typeof window === "undefined") return [];
try {
const events = getEvents();
const counts = new Map<string, { title: string; section: string; views: number }>();
for (const event of events) {
const existing = counts.get(event.slug);
if (existing) {
existing.views++;
} else {
counts.set(event.slug, {
slug: event.slug,
title: event.title,
section: event.section,
views: 1,
});
}
}
return Array.from(counts.values())
.sort((a, b) => b.views - a.views)
.slice(0, limit);
} catch {
return [];
}
}