diff --git a/frontend/src/App.css b/frontend/src/App.css index e1faa94..75ec723 100644 --- a/frontend/src/App.css +++ b/frontend/src/App.css @@ -2722,6 +2722,40 @@ body { font-weight: 500; } +.pipeline-events__view-toggle { + display: inline-flex; + border: 1px solid var(--color-border); + border-radius: 6px; + overflow: hidden; +} + +.pipeline-events__view-btn { + background: transparent; + border: none; + color: var(--color-text-secondary); + font-size: 0.75rem; + font-weight: 500; + padding: 0.25rem 0.625rem; + cursor: pointer; + font-family: inherit; + transition: background 0.15s, color 0.15s; +} + +.pipeline-events__view-btn:hover { + color: var(--color-text-primary); + background: var(--color-accent-subtle); +} + +.pipeline-events__view-btn--active { + background: var(--color-accent); + color: var(--color-bg-page); +} + +.pipeline-events__view-btn--active:hover { + background: var(--color-accent-hover); + color: var(--color-bg-page); +} + .pipeline-events__empty { font-size: 0.85rem; color: var(--color-text-muted); diff --git a/frontend/src/api/public-client.ts b/frontend/src/api/public-client.ts index b94f0a7..650da87 100644 --- a/frontend/src/api/public-client.ts +++ b/frontend/src/api/public-client.ts @@ -439,13 +439,14 @@ export async function fetchPipelineVideos(): Promise export async function fetchPipelineEvents( videoId: string, - params: { offset?: number; limit?: number; stage?: string; event_type?: string } = {}, + params: { offset?: number; limit?: number; stage?: string; event_type?: string; order?: "asc" | "desc" } = {}, ): Promise { const qs = new URLSearchParams(); if (params.offset !== undefined) qs.set("offset", String(params.offset)); if (params.limit !== undefined) qs.set("limit", String(params.limit)); if (params.stage) qs.set("stage", params.stage); if (params.event_type) qs.set("event_type", params.event_type); + if (params.order) qs.set("order", params.order); const query = qs.toString(); return request( `${BASE}/admin/pipeline/events/${videoId}${query ? `?${query}` : ""}`, diff --git a/frontend/src/pages/AdminPipeline.tsx b/frontend/src/pages/AdminPipeline.tsx index e38f2a0..f903ba0 100644 --- a/frontend/src/pages/AdminPipeline.tsx +++ b/frontend/src/pages/AdminPipeline.tsx @@ -103,13 +103,18 @@ function EventLog({ videoId }: { videoId: string }) { const [loading, setLoading] = useState(true); const [error, setError] = useState(null); const [offset, setOffset] = useState(0); + const [viewMode, setViewMode] = useState<"head" | "tail">("tail"); const limit = 50; const load = useCallback(async () => { setLoading(true); setError(null); try { - const res = await fetchPipelineEvents(videoId, { offset, limit }); + const res = await fetchPipelineEvents(videoId, { + offset, + limit, + order: viewMode === "head" ? "asc" : "desc", + }); setEvents(res.items); setTotal(res.total); } catch (err) { @@ -117,7 +122,7 @@ function EventLog({ videoId }: { videoId: string }) { } finally { setLoading(false); } - }, [videoId, offset]); + }, [videoId, offset, viewMode]); useEffect(() => { void load(); @@ -134,6 +139,20 @@ function EventLog({ videoId }: { videoId: string }) {
{total} event{total !== 1 ? "s" : ""} +
+ + +
diff --git a/frontend/tsconfig.app.tsbuildinfo b/frontend/tsconfig.app.tsbuildinfo index 997c8ec..c9f1734 100644 --- a/frontend/tsconfig.app.tsbuildinfo +++ b/frontend/tsconfig.app.tsbuildinfo @@ -1 +1 @@ -{"root":["./src/App.tsx","./src/main.tsx","./src/vite-env.d.ts","./src/api/client.ts","./src/api/public-client.ts","./src/components/ModeToggle.tsx","./src/components/ReportIssueModal.tsx","./src/components/StatusBadge.tsx","./src/pages/AdminPipeline.tsx","./src/pages/AdminReports.tsx","./src/pages/CreatorDetail.tsx","./src/pages/CreatorsBrowse.tsx","./src/pages/Home.tsx","./src/pages/MomentDetail.tsx","./src/pages/ReviewQueue.tsx","./src/pages/SearchResults.tsx","./src/pages/TechniquePage.tsx","./src/pages/TopicsBrowse.tsx"],"version":"5.6.3"} \ No newline at end of file +{"root":["./src/App.tsx","./src/main.tsx","./src/vite-env.d.ts","./src/api/client.ts","./src/api/public-client.ts","./src/components/AdminDropdown.tsx","./src/components/ModeToggle.tsx","./src/components/ReportIssueModal.tsx","./src/components/StatusBadge.tsx","./src/pages/AdminPipeline.tsx","./src/pages/AdminReports.tsx","./src/pages/CreatorDetail.tsx","./src/pages/CreatorsBrowse.tsx","./src/pages/Home.tsx","./src/pages/MomentDetail.tsx","./src/pages/ReviewQueue.tsx","./src/pages/SearchResults.tsx","./src/pages/TechniquePage.tsx","./src/pages/TopicsBrowse.tsx"],"version":"5.6.3"} \ No newline at end of file