# Phase 4: Frontend - Research **Researched:** 2026-02-24 **Domain:** React + TypeScript frontend integration with admin monitoring APIs **Confidence:** HIGH ## Summary Phase 4 wires the existing React/TypeScript/Tailwind frontend to the three admin API endpoints delivered in Phase 3: `GET /admin/health`, `GET /admin/analytics`, and `GET /admin/alerts` + `POST /admin/alerts/:id/acknowledge`. The frontend already has a complete admin-detection pattern, tab-based navigation, an axios-backed `adminService.ts`, and a `ProtectedRoute` component. The work is pure frontend integration — no new infrastructure, no new libraries, no new backend routes. The stack is locked: React 18 + TypeScript + Tailwind CSS + lucide-react icons + react-router-dom v6 + axios (via `adminService.ts`). The project uses `clsx` and `tailwind-merge` (via `cn()`) for conditional class composition. No charting library is installed. The existing `Analytics.tsx` component shows the styling and layout patterns to follow. The existing `UploadMonitoringDashboard.tsx` shows the health indicator pattern with colored circles. The primary implementation risk is the alert acknowledgement UX: after calling `POST /admin/alerts/:id/acknowledge`, the local state must update immediately (optimistic update or re-fetch) so the banner disappears without waiting for a full page refresh. The alert banner must render above the tab navigation because it is a global signal, not scoped to a specific tab. **Primary recommendation:** Add new components to the existing `monitoring` tab in App.tsx, extend `adminService.ts` with the three monitoring API methods, add an `AdminMonitoringDashboard` component, add an `AlertBanner` component that renders above the nav inside `Dashboard`, and add an `AdminRoute` wrapper that shows access-denied for non-admins who somehow hit the monitoring tab directly. --- ## Phase Requirements | ID | Description | Research Support | |----|-------------|-----------------| | ALRT-03 | Admin sees in-app alert banner for active critical issues; banner disappears after acknowledgement | alertBanner component using GET /admin/alerts + POST /admin/alerts/:id/acknowledge; optimistic state update on acknowledge | | ANLY-02 (UI) | Admin dashboard shows processing summary: upload counts, success/failure rates, avg processing time | AdminMonitoringDashboard section consuming GET /admin/analytics response shape (AnalyticsSummary interface) | | HLTH-01 (UI) | Admin dashboard shows health status indicators (green/yellow/red) for all four services with last-checked timestamp | ServiceHealthPanel component consuming GET /admin/health; status → color mapping green=healthy, yellow=degraded, red=down/unknown | *Note: ANLY-02 and HLTH-01 were marked Complete in Phase 3 (backend side). Phase 4 completes their UI delivery.* --- ## Standard Stack ### Core (already installed — no new packages needed) | Library | Version | Purpose | Why Standard | |---------|---------|---------|--------------| | react | ^18.2.0 | Component rendering | Project standard | | typescript | ^5.2.2 | Type safety | Project standard | | tailwindcss | ^3.3.5 | Utility CSS | Project standard | | lucide-react | ^0.294.0 | Icons (AlertTriangle, CheckCircle, Activity, Clock, etc.) | Already used throughout | | axios | ^1.6.2 | HTTP client (via adminService) | Already used in adminService.ts | | clsx + tailwind-merge | ^2.0.0 / ^2.0.0 | Conditional class composition via `cn()` | Already used in Analytics.tsx | | react-router-dom | ^6.20.1 | Routing, Navigate | Already used | ### No New Libraries Required All required UI capabilities exist in the current stack: - Status indicators: plain `div` with Tailwind bg-green-500 / bg-yellow-500 / bg-red-500 - Alert banner: fixed/sticky div above nav, standard Tailwind layout - Timestamps: `new Date(ts).toLocaleString()` or `toRelative()` — no date library needed - Loading state: existing spinner pattern (`animate-spin rounded-full border-b-2`) **Installation:** None required. --- ## Architecture Patterns ### Recommended File Changes ``` frontend/src/ ├── components/ │ ├── AlertBanner.tsx # NEW — global alert banner above nav │ ├── AdminMonitoringDashboard.tsx # NEW — health + analytics panel │ └── (existing files unchanged) ├── services/ │ └── adminService.ts # EXTEND — add getHealth(), getAnalytics(), getAlerts(), acknowledgeAlert() └── App.tsx # MODIFY — render AlertBanner, wire monitoring tab to new component ``` ### Pattern 1: Alert Banner — global, above nav, conditional render **What:** A dismissible/acknowledgeable banner rendered inside `Dashboard` ABOVE the `