16 KiB
Requirements Document
Introduction
Signal Dashboard is a single-page application (SPA) frontend for the Stock Data Backend API. The Dashboard provides authenticated users with a visual interface to monitor watchlists, analyze individual tickers across multiple dimensions (technical, S/R, sentiment, fundamentals, momentum), scan for asymmetric risk:reward trade setups, view composite-score rankings, and manage system administration. The Dashboard consumes the existing REST API at /api/v1/ and is served as static files by Nginx on the same domain (signal.thiessen.io).
Technology choice: React 18 + TypeScript + Vite, with TanStack Query for data fetching, Zustand for auth state, Tailwind CSS for styling, Recharts for charting, and React Router for navigation. This stack prioritizes maintainability, small bundle size, and a modern developer experience without framework bloat.
Glossary
- Dashboard: The Signal Dashboard SPA frontend application
- API_Client: The HTTP client module that communicates with the backend REST API
- Auth_Module: The authentication subsystem handling login, registration, token storage, and token refresh
- Watchlist_View: The main overview page displaying the user's watchlist entries with enriched score data
- Ticker_Detail_View: The per-ticker analysis page showing price chart, indicators, S/R levels, sentiment, and fundamentals
- Scanner_View: The trade setup scanner page displaying R:R filtered setups
- Rankings_View: The page displaying all tickers sorted by composite score
- Admin_Panel: The administration interface for user management, job control, system settings, and data cleanup
- Router: The client-side routing module controlling navigation and access guards
- Token_Store: The client-side storage mechanism for JWT access tokens
- Chart_Component: The interactive price chart component rendering OHLCV candlestick data with overlays
- Score_Card: A UI component displaying a composite score and its dimension breakdown
- Toast_System: The notification subsystem displaying transient success/error messages to the user
Requirements
Requirement 1: JWT Authentication Flow
User Story: As a user, I want to log in and register so that I can access the dashboard securely.
Acceptance Criteria
- WHEN a user submits valid credentials on the login form, THE Auth_Module SHALL send a POST request to
/api/v1/auth/loginand store the returned JWT token in the Token_Store - WHEN a user submits a registration form with a username (minimum 1 character) and password (minimum 6 characters), THE Auth_Module SHALL send a POST request to
/api/v1/auth/registerand display a success message via the Toast_System - WHILE a valid JWT token exists in the Token_Store, THE API_Client SHALL include the token as a Bearer authorization header on all subsequent API requests
- WHEN the API returns a 401 Unauthorized response, THE Auth_Module SHALL clear the Token_Store and redirect the user to the login page
- IF the login or registration request fails, THEN THE Auth_Module SHALL display the error message from the API response via the Toast_System
- THE Token_Store SHALL persist the JWT token in browser localStorage so that sessions survive page reloads
Requirement 2: Protected Routing and Role-Based Access
User Story: As a user, I want the app to enforce access control so that unauthenticated users cannot access protected pages and only admins can access admin features.
Acceptance Criteria
- WHILE no valid JWT token exists in the Token_Store, THE Router SHALL redirect navigation to any protected route to the login page
- WHILE a valid JWT token exists in the Token_Store, THE Router SHALL allow navigation to protected routes (Watchlist_View, Ticker_Detail_View, Scanner_View, Rankings_View)
- WHILE the authenticated user has an admin role, THE Router SHALL allow navigation to the Admin_Panel
- WHILE the authenticated user has a non-admin role, THE Router SHALL redirect navigation to the Admin_Panel to the Watchlist_View
- THE Router SHALL provide a navigation sidebar or top bar with links to all accessible views for the authenticated user
Requirement 3: Watchlist Overview
User Story: As a user, I want to see my watchlist with composite scores, dimension breakdowns, and R:R ratios so that I can quickly assess my tracked tickers.
Acceptance Criteria
- WHEN the Watchlist_View loads, THE Dashboard SHALL fetch data from
GET /api/v1/watchlistand display each entry as a card or row - THE Watchlist_View SHALL display for each entry: symbol, entry type (auto/manual), composite score, dimension scores, R:R ratio, R:R direction, and nearest S/R levels
- WHEN a user clicks the add-to-watchlist control and enters a valid ticker symbol, THE Dashboard SHALL send a POST request to
/api/v1/watchlist/{symbol}and refresh the watchlist - WHEN a user clicks the remove button on a watchlist entry, THE Dashboard SHALL send a DELETE request to
/api/v1/watchlist/{symbol}and remove the entry from the display - IF the watchlist API request fails, THEN THE Dashboard SHALL display the error message via the Toast_System
- WHEN a user clicks on a watchlist entry symbol, THE Router SHALL navigate to the Ticker_Detail_View for that symbol
- THE Watchlist_View SHALL visually distinguish auto-populated entries from manual entries using a badge or label
Requirement 4: Ticker Detail View
User Story: As a user, I want to see a comprehensive analysis of a single ticker including price chart, indicators, S/R levels, sentiment, and fundamentals so that I can make informed decisions.
Acceptance Criteria
- WHEN the Ticker_Detail_View loads for a given symbol, THE Dashboard SHALL fetch data in parallel from:
GET /api/v1/ohlcv/{symbol},GET /api/v1/scores/{symbol},GET /api/v1/sr-levels/{symbol},GET /api/v1/sentiment/{symbol}, andGET /api/v1/fundamentals/{symbol} - THE Chart_Component SHALL render OHLCV data as a candlestick chart with date on the x-axis and price on the y-axis
- THE Chart_Component SHALL overlay S/R levels as horizontal lines on the price chart, color-coded by type (support in green, resistance in red)
- THE Ticker_Detail_View SHALL display the composite score and all dimension scores using Score_Card components
- THE Ticker_Detail_View SHALL display sentiment data including classification (bullish/bearish/neutral), confidence, and the time-decay weighted dimension score
- THE Ticker_Detail_View SHALL display fundamental data including P/E ratio, revenue growth, earnings surprise, and market cap
- WHEN a user selects an indicator type (ADX, EMA, RSI, ATR, volume_profile, pivot_points), THE Dashboard SHALL fetch data from
GET /api/v1/indicators/{symbol}/{indicator_type}and display the result with its normalized score - WHEN a user requests the EMA cross signal, THE Dashboard SHALL fetch data from
GET /api/v1/indicators/{symbol}/ema-crossand display the signal (bullish/bearish/neutral) with short and long EMA values - IF any data fetch fails for the Ticker_Detail_View, THEN THE Dashboard SHALL display an inline error message for the failed section while rendering the remaining sections normally
Requirement 5: Trade Setup Scanner
User Story: As a user, I want to scan for trade setups with favorable risk:reward ratios so that I can find asymmetric opportunities.
Acceptance Criteria
- WHEN the Scanner_View loads, THE Dashboard SHALL fetch data from
GET /api/v1/tradesand display all trade setups in a sortable table - THE Scanner_View SHALL display for each trade setup: symbol, direction (long/short), entry price, stop loss, target, R:R ratio, composite score, and detection timestamp
- THE Scanner_View SHALL allow the user to filter trade setups by minimum R:R ratio using a numeric input
- THE Scanner_View SHALL allow the user to filter trade setups by direction (long, short, or both)
- THE Scanner_View SHALL allow the user to sort the table by any column (R:R ratio, composite score, symbol, detection time)
- WHEN a user clicks on a trade setup symbol, THE Router SHALL navigate to the Ticker_Detail_View for that symbol
Requirement 6: Rankings View
User Story: As a user, I want to see all tickers ranked by composite score so that I can identify the strongest opportunities.
Acceptance Criteria
- WHEN the Rankings_View loads, THE Dashboard SHALL fetch data from
GET /api/v1/rankingsand display tickers sorted by composite score descending - THE Rankings_View SHALL display for each ticker: rank position, symbol, composite score, and all dimension scores
- THE Rankings_View SHALL display the current scoring weights used for composite calculation
- WHEN a user clicks on a ranked ticker symbol, THE Router SHALL navigate to the Ticker_Detail_View for that symbol
Requirement 7: Admin Panel — User Management
User Story: As an admin, I want to manage user accounts so that I can control access to the platform.
Acceptance Criteria
- WHEN the Admin_Panel user management section loads, THE Dashboard SHALL fetch data from
GET /api/v1/admin/usersand display all users in a table - THE Admin_Panel SHALL display for each user: username, role, and access status
- WHEN an admin clicks the create-user control and submits a username, password, role, and access flag, THE Dashboard SHALL send a POST request to
/api/v1/admin/usersand refresh the user list - WHEN an admin toggles a user's access status, THE Dashboard SHALL send a PUT request to
/api/v1/admin/users/{user_id}/accesswith the new access flag - WHEN an admin resets a user's password, THE Dashboard SHALL send a PUT request to
/api/v1/admin/users/{user_id}/passwordwith the new password - IF any admin user management request fails, THEN THE Dashboard SHALL display the error message via the Toast_System
Requirement 8: Admin Panel — System Settings and Jobs
User Story: As an admin, I want to manage system settings, scheduled jobs, and data cleanup so that I can maintain the platform.
Acceptance Criteria
- WHEN the Admin_Panel settings section loads, THE Dashboard SHALL fetch data from
GET /api/v1/admin/settingsand display all settings as editable fields - WHEN an admin updates a system setting value, THE Dashboard SHALL send a PUT request to
/api/v1/admin/settings/{key}with the new value - WHEN an admin toggles the registration setting, THE Dashboard SHALL send a PUT request to
/api/v1/admin/settings/registrationwith the enabled flag - WHEN an admin toggles a scheduled job on or off, THE Dashboard SHALL send a PUT request to
/api/v1/admin/jobs/{job_name}/togglewith the enabled flag - WHEN an admin triggers a scheduled job manually, THE Dashboard SHALL send a POST request to
/api/v1/admin/jobs/{job_name}/triggerand display a confirmation via the Toast_System - WHEN an admin submits a data cleanup request with an older-than-days value, THE Dashboard SHALL send a POST request to
/api/v1/admin/data/cleanupwith the specified value and display the result via the Toast_System
Requirement 9: Ticker Management
User Story: As a user, I want to add and remove tickers from the system so that I can track the stocks I care about.
Acceptance Criteria
- WHEN a user submits a new ticker symbol via the add-ticker form, THE Dashboard SHALL send a POST request to
/api/v1/tickerswith the symbol and refresh the ticker list - WHEN a user views the ticker list, THE Dashboard SHALL fetch data from
GET /api/v1/tickersand display all registered tickers - WHEN a user clicks the delete button on a ticker, THE Dashboard SHALL display a confirmation dialog before sending a DELETE request to
/api/v1/tickers/{symbol} - IF a ticker deletion or creation request fails, THEN THE Dashboard SHALL display the error message via the Toast_System
- WHEN a ticker is successfully deleted, THE Dashboard SHALL remove the ticker from the displayed list without requiring a full page reload
Requirement 10: Data Ingestion Trigger
User Story: As a user, I want to manually trigger data ingestion for a specific ticker so that I can get fresh data on demand.
Acceptance Criteria
- WHEN a user clicks the fetch-data button on the Ticker_Detail_View, THE Dashboard SHALL send a POST request to
/api/v1/ingestion/fetch/{symbol} - WHILE the ingestion request is in progress, THE Dashboard SHALL display a loading indicator on the fetch-data button
- WHEN the ingestion request completes successfully, THE Dashboard SHALL display a success message via the Toast_System and refresh the OHLCV data on the Ticker_Detail_View
- IF the ingestion request fails, THEN THE Dashboard SHALL display the error message via the Toast_System
Requirement 11: Score Weight Configuration
User Story: As a user, I want to adjust the scoring dimension weights so that I can customize the composite score calculation to my strategy.
Acceptance Criteria
- THE Dashboard SHALL display the current scoring weights on the Rankings_View with editable numeric inputs for each dimension
- WHEN a user modifies one or more weight values and submits the form, THE Dashboard SHALL send a PUT request to
/api/v1/scores/weightswith the updated weights map - WHEN the weight update succeeds, THE Dashboard SHALL refresh the rankings data to reflect the new composite scores
- IF the weight update request fails, THEN THE Dashboard SHALL display the error message via the Toast_System
Requirement 12: API Client and Error Handling
User Story: As a developer, I want a centralized API client with consistent error handling so that all API interactions follow the same patterns.
Acceptance Criteria
- THE API_Client SHALL send all requests to the base URL
/api/v1/using the JSON content type - THE API_Client SHALL unwrap the API envelope (
{ status, data, error }) and return thedatafield on success or throw an error with theerrorfield on failure - THE API_Client SHALL attach the JWT Bearer token from the Token_Store to every authenticated request
- WHEN the API_Client receives a network error or timeout, THE API_Client SHALL throw a descriptive error that the calling component can display via the Toast_System
- THE API_Client SHALL set a request timeout of 30 seconds for all API calls
Requirement 13: Responsive Layout and Visual Design
User Story: As a user, I want the dashboard to have a clean, modern interface that works on desktop and tablet screens so that I can use it comfortably.
Acceptance Criteria
- THE Dashboard SHALL use a sidebar navigation layout on screens wider than 1024 pixels and a collapsible hamburger menu on narrower screens
- THE Dashboard SHALL use a dark color scheme with accent colors for positive (green) and negative (red) values consistent with financial data conventions
- THE Dashboard SHALL apply smooth transitions (duration 150ms to 300ms) for page navigation, modal openings, and interactive element state changes
- THE Dashboard SHALL display numeric financial values with appropriate formatting: prices to 2 decimal places, percentages with a percent sign, large numbers with abbreviations (K, M, B)
- THE Dashboard SHALL display loading skeleton placeholders while data is being fetched from the API
Requirement 14: Static SPA Build and Deployment
User Story: As a developer, I want the frontend to build as static files that Nginx can serve alongside the backend API so that deployment is simple.
Acceptance Criteria
- THE Dashboard SHALL produce a static build output (HTML, CSS, JS) in a
dist/directory via a single build command - THE Dashboard SHALL use hash-based filenames for JS and CSS assets to enable long-term browser caching
- THE Dashboard SHALL support client-side routing with a fallback to
index.htmlfor all non-API routes (Nginxtry_filesconfiguration) - THE Dashboard SHALL proxy API requests to
/api/v1/on the same origin, requiring no CORS configuration in production - WHEN the
GET /api/v1/healthendpoint returns a success response, THE Dashboard SHALL consider the backend available