From 3a6b2e86287f259fdfed10134bc1110bd596fdc0 Mon Sep 17 00:00:00 2001 From: Victor Giers Date: Thu, 8 Jan 2026 01:56:38 +0100 Subject: [PATCH] Create RandomEntryRedirect component --- client/src/pages/RandomEntryRedirect.tsx | 42 ++++++++++++++++++++++++ 1 file changed, 42 insertions(+) create mode 100644 client/src/pages/RandomEntryRedirect.tsx diff --git a/client/src/pages/RandomEntryRedirect.tsx b/client/src/pages/RandomEntryRedirect.tsx new file mode 100644 index 0000000..280c0bc --- /dev/null +++ b/client/src/pages/RandomEntryRedirect.tsx @@ -0,0 +1,42 @@ +import { useEffect, useState } from 'react'; +import { useNavigate, useSearchParams } from 'react-router-dom'; +import { fetchEntries } from '../api'; +import type { EntrySummary } from '../types'; + +export default function RandomEntryRedirect() { + const [loading, setLoading] = useState(true); + const [error, setError] = useState(null); + const [params] = useSearchParams(); + const navigate = useNavigate(); + + useEffect(() => { + let cancelled = false; + const run = async () => { + try { + const entries: EntrySummary[] = await fetchEntries(); + if (!entries.length) { + throw new Error('No entries available'); + } + const idx = Math.floor(Math.random() * entries.length); + const entry = entries[idx]; + if (!cancelled) { + navigate(`/entry/${encodeURIComponent(entry.id)}${params.toString() ? `?${params.toString()}` : ''}`, { replace: true }); + } + } catch (err: any) { + if (!cancelled) { + setError(err?.message || 'Could not pick a random entry'); + } + } finally { + if (!cancelled) setLoading(false); + } + }; + run(); + return () => { + cancelled = true; + }; + }, [navigate, params]); + + if (loading) return
Picking a random reel…
; + if (error) return
{error}
; + return null; +}