Files
unified-media-manager/docs/UX-FLOWS.md
2026-04-24 10:45:19 -07:00

12 KiB
Raw Blame History

UMM UX Flows — Implemented & Tested

Last verified: 2026-04-22 (deployed build, backend healthy)

Navigation

Route Page Nav Label
/ Dashboard Dashboard
/library Library Library
/library/:type/:id Media Detail (via Library click)
/discover Discover Discover
/calendar Calendar Calendar
/queue Download Queue Queue
/search Search Indexers Search
/activity Activity Activity
/requests Requests Requests
/blocklist Blocklist Blocklist
/settings Settings Settings

Page-by-Page Flows

Dashboard (/)

API: GET /api/dashboard (200 OK)

  • 8 stat cards: Movies, TV Series, Music, Books, Active Downloads, Missing, Upgrades Available, Total Storage
  • Auto-fetches on mount
  • Skeleton loading while fetching
  • Error banner with retry on failure

Library (/library)

API: GET /api/media?page=1&page_size=50 (200 OK)

  • Search input with 300ms debounce
  • Type filter: All, Movie, Series, Music, Book, Audiobook, Podcast, Photo, Other
  • Status filter: All, Available, Unavailable, Downloading, Failed
  • Paginated table (50 per page)
  • Each row: Title (click → detail), Type, Status badge, Quality, Monitor toggle
  • Monitor toggle: optimistic update, rollback on error with toast
  • Empty state messages for no results vs empty library

Media Detail (/library/:type/:id)

API: GET /api/media/:type/:id/detail (200 OK)

5 tabs (4 for non-series):

Overview tab:

  • Poster image (or letter placeholder)
  • Title, year, original title
  • Status badge, monitored indicator
  • TMDB rating, genres
  • Quality profile name
  • Current quality / desired quality
  • Synopsis text

Search tab:

  • Auto-searches indexers for media title
  • Results via ReleaseSearchResults component
  • Sortable by quality, size, seeders, age

Files tab:

  • File table: name, quality, size, source, codec, subtitles
  • Per-file subtitle badges (language code, SDH, Forced, source)
  • "Search" button per file → subtitle search modal
  • "Download" button per subtitle result
  • "Extract All Subtitles" button (extracts embedded subs)

Episodes tab (series only):

  • Episodes grouped by season
  • Columns: episode #, title, status, monitored, has file, quality

History tab:

  • Timeline with color-coded badges: Grab, Import, Download, Failed, Upgrade, Blocked, Error
  • Relative timestamps (Xm ago, Xh ago, Xd ago)

Header actions:

  • "Refresh Metadata" button → POST /api/media/:type/:id/refresh-metadata
  • "Delete" button → confirmation modal → DELETE /api/media/:type/:id → redirect to Library

Discover (/discover)

API: GET /api/discover/trending?type=movie&page=1 (401 — requires API key auth) API: GET /api/discover/popular?type=movie&page=1 (401 — requires API key auth)

  • Trending / Popular tab toggle
  • Movie / Series type filter
  • Poster grid with hover overlay (title, year, rating, "Add to Library" button)
  • Green checkmark badge for items already in library
  • "Add to Library" → POST /api/discover/add → toast feedback
  • Paginated (prev/next, up to page 10)

Note: Requires API key authentication. Frontend does not currently send API keys, so this flow will 401 in production.

Calendar (/calendar)

API: GET /api/calendar?month=2026-04 (200 OK)

  • Monthly grid (6 rows × 7 cols)
  • Navigation: prev/next month, "Today" button
  • Events color-coded by type: movie (indigo), series (emerald), music (amber), audiobook (rose), podcast (violet)
  • Click event → navigate to media detail
  • "Today" date highlighted with indigo ring
  • "+N more" for days with >3 events

Download Queue (/queue)

API: GET /api/queue (200 OK)

  • Tabs: All, Downloading, Pending, Failed, Imported, History
  • Auto-refresh every 5 seconds
  • Per-item: release title, status badge, download client, quality, size
  • Progress bar for downloading items
  • Error message display for failed items
  • Actions: Cancel (with confirmation modal), Retry, Retry All Failed, Clear Completed
  • "Check for Completed Downloads" → POST /api/imports/trigger
  • Import History tab with pagination (GET /api/imports/history)

API: GET /api/releases/search?query=... (500 — "no enabled indexers available" when none configured)

  • Free-text search across all enabled indexers
  • Sortable columns: Quality, Title, Size, Indexer, Seeders, Age
  • "Select & Grab" button per result → opens media selector modal
    • Modal: debounced library search
    • Select media item → POST /api/releases/grab → toast
  • Empty state for no query, no results, loading skeleton

Note: Returns 500 when no indexers are configured. This is expected behavior.

Activity (/activity)

API: GET /api/activity?page=1&page_size=50 (200 OK)

  • Paginated event log (50 per page)
  • Type filter dropdown: All, Grabs, Imports, Downloads, Failures, Upgrades, Safety Blocks, Errors
  • Color-coded badges: Grab (blue), Import/Download (green), Failed/Error (red), Upgrade (purple), Blocked (orange)
  • Relative timestamps

Requests (/requests)

API: GET /api/requests?page=1&page_size=20 (401 — requires API key auth)

  • Filter tabs: All, Pending, Approved, Fulfilled, Rejected
  • "+ New Request" modal:
    • Title (required), Type (7 options), Year, Quality Profile dropdown, Root Folder dropdown
    • Submit → POST /api/requests
  • Per-request card: title, year, status badge, requester, time ago, quality profile, root folder
  • Actions for pending: Approve (green) → PUT /api/requests/:id/approve, Reject (red, with confirmation) → PUT /api/requests/:id/reject
  • Withdraw link for pending/approved → DELETE /api/requests/:id

Note: Requires API key authentication. Frontend does not currently send API keys.

Blocklist (/blocklist)

API: GET /api/blocklist?page=1&page_size=50 (200 OK)

  • Paginated table (50 per page)
  • Checkboxes for bulk selection (select all toggle)
  • Per-row: release title, indexer, quality, reason, date, delete button
  • Bulk "Delete Selected" → DELETE /api/blocklist/:id per item
  • "Clear Expired" → DELETE /api/blocklist/expired
  • "Clear All" → confirmation modal → DELETE /api/blocklist

Settings (/settings)

8 sections in 2-column grid layout:

Notifications

API: GET /api/notifications/channels (200 OK)

  • List channels with enable/disable dot, name, type badge (webhook/telegram), config preview
  • Inline edit: name, URL/bot token/chat ID, event type checkboxes (8 types), save/cancel/test/delete
  • Add channel: name, type selector, URL or bot token + chat ID, event type checkboxes
  • Test button → POST /api/notifications/channels/:id/test

Indexers

API: GET /api/indexers (200 OK)

  • List with enable/disable dot, name, implementation badge (torznab/newznab/cardigann), URL
  • Inline edit: name, URL, API key (masked), enable toggle, save/cancel/test/delete
  • Add indexer: name, implementation selector (Newznab, Torznab, Cardigann)
    • Cardigann: YAML textarea, validate button → POST /api/indexers/validate-cardigann, settings fields from definition
  • Test → POST /api/indexers/:id/test

Download Clients

API: GET /api/download-clients (200 OK)

  • List with enable/disable dot, name, implementation, URL
  • Inline edit: name, URL, API key, category, priority, enable toggle, save/cancel/test/delete
  • Add: name, implementation (SABnzbd, qBittorrent), URL, API key
  • Test → POST /api/download-clients/:id/test

Quality Profiles

API: GET /api/quality-profiles (200 OK)

  • List with name, media type badges
  • Inline edit: name, cutoff quality, allowed qualities (comma-sep), save/cancel/delete
  • Add: name, media types (comma-sep), cutoff quality, allowed qualities

Root Folders

API: GET /api/root-folders (200 OK)

  • List with path, media type, free space
  • Inline edit: path, media type (delete + re-create pattern), save/cancel/delete
  • Add: path, media type

Tags

API: GET /api/tags (200 OK — fixed)

  • List with name, color swatch
  • Inline edit: name, color, save/cancel/delete
  • Add: name, color (hex)

Tasks

API: GET /api/workers (401 — requires API key auth, different from /api/tasks)

  • Scheduled tasks list with name, cron expression, enabled toggle, last run, next run
  • Enable/disable toggle per task

Note: Frontend calls /api/tasks but router registers /api/workers. May result in 404.

Metadata

API: POST /api/media/refresh-all (200 OK, no auth required)

  • Description text about refresh scope
  • "Refresh All Metadata" button → confirmation modal → POST
  • Loading state while refreshing

Shared Components

Component Used By Purpose
Toast All pages Success/error feedback (top-right, auto-dismiss)
ConfirmModal Queue, Blocklist, Media Detail, Settings, Requests Confirmation for destructive/batch actions
Pagination Library, Queue, Activity, Blocklist, Requests Page navigation with total/pages display
StatusBadge Library, Queue, Media Detail, Requests Color-coded status labels
ErrorBanner All pages Error display with retry button
Loading Dashboard, Queue, Activity, Blocklist, Settings Skeleton/spinner loading states
ReleaseSearchResults Media Detail, Search Release result table with grab actions

API Test Results (2026-04-22)

Working (200 OK)

Endpoint Status Notes
GET /health/live 200 {"status":"alive"}
GET /api/dashboard 200 Stats returned, all zeros (empty DB)
GET /api/media 200 Paginated, empty
GET /api/queue 200 Empty
GET /api/blocklist 200 Paginated, empty
GET /api/activity 200 Paginated, empty
GET /api/indexers 200 Empty
GET /api/download-clients 200 Empty
GET /api/quality-profiles 200 Empty
GET /api/root-folders 200 Empty
GET /api/tags 200 Empty (fixed: removed created_at column ref)
GET /api/notifications/channels 200 Empty
GET /api/calendar 200 Empty events
GET /api/search 200 Empty results
GET /api/imports/history 200 Empty
POST /api/media/refresh-all 200 Triggers refresh

Auth-Required (401 Unauthorized)

Endpoint Notes
GET /api/requests API key auth middleware
GET /api/discover/trending API key auth middleware
GET /api/discover/popular API key auth middleware
GET /api/workers API key auth middleware

Root cause: Frontend client.ts does not send X-API-Key header or api_key query param. These flows (Requests, Discover, Tasks) will 401 in production unless auth is configured or the frontend is updated to pass API keys.

Expected Errors (500)

Endpoint Error Cause
GET /api/releases/search "no enabled indexers available" No indexers configured yet

Known Issues

  1. Auth-protected endpoints unreachable from frontend — Requests, Discover, and Tasks pages will show errors because the API client doesn't pass API keys. The newAPIKeyAuth middleware requires X-API-Key header or api_key query param.

  2. Tasks page route mismatch — Frontend calls /api/tasks but router registers workers at /api/workers. Needs alignment.

  3. No indexers configured — Release search (used by Search page and Media Detail Search tab) returns 500. Expected until indexers are added via Settings.

  4. Frontend CORS — CORS is configured to allow cfg.FrontendURL only. Requests from other origins will be rejected.