feat: add Force re-run checkbox to dashboard params

Adds a 'Force re-run' checkbox that passes force=True to the backend,
bypassing all date-based skip checks (scan, pipeline, portfolio, execution).

Also fixes auto run: ticker is not required (scan discovers tickers),
portfolio_id is the correct required field instead.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Ahmet Guzererler 2026-03-24 00:31:16 +01:00
parent 80a54b2411
commit 2a17ea0cca
1 changed files with 17 additions and 3 deletions

View File

@ -8,6 +8,7 @@ import {
IconButton, IconButton,
Button, Button,
Input, Input,
Checkbox,
useDisclosure, useDisclosure,
Drawer, Drawer,
DrawerOverlay, DrawerOverlay,
@ -50,6 +51,7 @@ interface RunParams {
date: string; date: string;
ticker: string; ticker: string;
portfolio_id: string; portfolio_id: string;
force: boolean;
} }
const RUN_TYPE_LABELS: Record<RunType, string> = { const RUN_TYPE_LABELS: Record<RunType, string> = {
@ -64,7 +66,7 @@ const REQUIRED_PARAMS: Record<RunType, (keyof RunParams)[]> = {
scan: ['date'], scan: ['date'],
pipeline: ['ticker', 'date'], pipeline: ['ticker', 'date'],
portfolio: ['date', 'portfolio_id'], portfolio: ['date', 'portfolio_id'],
auto: ['date', 'ticker'], auto: ['date', 'portfolio_id'],
}; };
/** Return the colour token for a given event type. */ /** Return the colour token for a given event type. */
@ -312,6 +314,7 @@ export const Dashboard: React.FC = () => {
date: new Date().toISOString().split('T')[0], date: new Date().toISOString().split('T')[0],
ticker: 'AAPL', ticker: 'AAPL',
portfolio_id: 'main_portfolio', portfolio_id: 'main_portfolio',
force: false,
}); });
// Auto-scroll the terminal to the bottom as new events arrive // Auto-scroll the terminal to the bottom as new events arrive
@ -335,7 +338,7 @@ export const Dashboard: React.FC = () => {
// Validate required params // Validate required params
const required = REQUIRED_PARAMS[type]; const required = REQUIRED_PARAMS[type];
const missing = required.filter((k) => !params[k]?.trim()); const missing = required.filter((k) => { const v = params[k]; return typeof v === 'string' ? !v.trim() : !v; });
if (missing.length > 0) { if (missing.length > 0) {
toast({ toast({
title: `Missing required fields for ${RUN_TYPE_LABELS[type]}`, title: `Missing required fields for ${RUN_TYPE_LABELS[type]}`,
@ -357,6 +360,7 @@ export const Dashboard: React.FC = () => {
portfolio_id: params.portfolio_id, portfolio_id: params.portfolio_id,
date: params.date, date: params.date,
ticker: params.ticker, ticker: params.ticker,
force: params.force,
}); });
setActiveRunId(res.data.run_id); setActiveRunId(res.data.run_id);
} catch (err) { } catch (err) {
@ -529,8 +533,18 @@ export const Dashboard: React.FC = () => {
onChange={(e) => setParams((p) => ({ ...p, portfolio_id: e.target.value }))} onChange={(e) => setParams((p) => ({ ...p, portfolio_id: e.target.value }))}
/> />
</HStack> </HStack>
<HStack>
<Checkbox
size="sm"
colorScheme="orange"
isChecked={params.force}
onChange={(e) => setParams((p) => ({ ...p, force: e.target.checked }))}
>
<Text fontSize="xs" color="orange.300">Force re-run (ignore cached results)</Text>
</Checkbox>
</HStack>
<Text fontSize="2xs" color="whiteAlpha.400"> <Text fontSize="2xs" color="whiteAlpha.400">
Required: Scan date · Pipeline ticker, date · Portfolio date, portfolio · Auto date, ticker Required: Scan date · Pipeline ticker, date · Portfolio date, portfolio · Auto date, portfolio
</Text> </Text>
</VStack> </VStack>
</Box> </Box>