Add Fetch Request pipeline UI with real-time SSEs #8
@@ -264,10 +264,13 @@ export default function FetchRequestDetail() {
|
||||
const isCompleted = index < activeStep;
|
||||
const isActive = index === activeStep;
|
||||
const isPaused = req.status === "paused" && isActive;
|
||||
const isFailed = req.status === "failed" && isActive;
|
||||
|
||||
let icon: React.ReactNode;
|
||||
if (isCompleted) {
|
||||
icon = <CheckCircleIcon sx={{ color: "success.main" }} />;
|
||||
} else if (isFailed) {
|
||||
icon = <ErrorIcon sx={{ color: "error.main" }} />;
|
||||
} else if (isPaused) {
|
||||
icon = <WarningAmberIcon sx={{ color: "warning.main" }} />;
|
||||
} else if (isActive) {
|
||||
|
||||
@@ -30,6 +30,7 @@ import {
|
||||
InputLabel,
|
||||
FormControl,
|
||||
OutlinedInput,
|
||||
Autocomplete,
|
||||
} from "@mui/material";
|
||||
import DeleteIcon from "@mui/icons-material/Delete";
|
||||
import CloudUploadIcon from "@mui/icons-material/CloudUpload";
|
||||
@@ -56,6 +57,7 @@ import type {
|
||||
} from "./features/fetch-requests";
|
||||
import { RETRY_MAX } from "./features/fetch-requests";
|
||||
import { useNavigate } from "react-router-dom";
|
||||
import { useResourceByName, useConfig } from "../react-openapi";
|
||||
|
||||
const statusColors: Record<FetchRequestStatus, "default" | "primary" | "warning" | "info" | "success" | "error"> = {
|
||||
pending: "default",
|
||||
@@ -119,6 +121,16 @@ export default function FetchRequests() {
|
||||
...(accountFilter ? { account_name: accountFilter } : {}),
|
||||
...(sourceFilter !== "all" ? { source_type: sourceFilter } : {}),
|
||||
});
|
||||
const { useList: useAccountsList } = useResourceByName("accounts");
|
||||
const { data: accountsData } = useAccountsList();
|
||||
const accountOptions: string[] = React.useMemo(() => {
|
||||
return (accountsData?.data ?? []).map((a: any) => a.name).filter(Boolean);
|
||||
}, [accountsData]);
|
||||
|
||||
const config = useConfig();
|
||||
const fetchRes = config?.resources.find((r: any) => r.name === "fetch-requests");
|
||||
const formatOptions: string[] = (fetchRes?.fields?.source?.schema?.format?.options as string[]) ?? ["axis", "icici_ocr"];
|
||||
|
||||
const createMutation = useCreateFetchRequest();
|
||||
const updateMutation = useUpdateFetchRequest();
|
||||
const deleteMutation = useDeleteFetchRequest();
|
||||
@@ -253,18 +265,40 @@ export default function FetchRequests() {
|
||||
Uploaded as: {uploadedPath}
|
||||
</Alert>
|
||||
)}
|
||||
<TextField label="Format (csv, pdf, ...)" value={format} onChange={(e) => setFormat(e.target.value)} size="small" />
|
||||
<FormControl size="small">
|
||||
<InputLabel>Format</InputLabel>
|
||||
<Select value={format} onChange={(e) => setFormat(e.target.value)} label="Format">
|
||||
{formatOptions.map((opt) => (
|
||||
<MenuItem key={opt} value={opt}>{opt}</MenuItem>
|
||||
))}
|
||||
</Select>
|
||||
</FormControl>
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
<TextField label="Format" value={format} onChange={(e) => setFormat(e.target.value)} size="small" helperText="e.g. email, pdf, csv" />
|
||||
<FormControl size="small">
|
||||
<InputLabel>Format</InputLabel>
|
||||
<Select value={format} onChange={(e) => setFormat(e.target.value)} label="Format">
|
||||
{formatOptions.map((opt) => (
|
||||
<MenuItem key={opt} value={opt}>{opt}</MenuItem>
|
||||
))}
|
||||
</Select>
|
||||
</FormControl>
|
||||
<TextField label="From Email" value={fromEmail} onChange={(e) => setFromEmail(e.target.value)} size="small" />
|
||||
<TextField label="Subject" value={subject} onChange={(e) => setSubject(e.target.value)} size="small" />
|
||||
<TextField label="Raw Terms" value={rawTerms} onChange={(e) => setRawTerms(e.target.value)} size="small" helperText="Comma-separated search terms" />
|
||||
</>
|
||||
)}
|
||||
|
||||
<TextField label="Account Name" value={accountName} onChange={(e) => setAccountName(e.target.value)} size="small" required />
|
||||
<Autocomplete
|
||||
options={accountOptions}
|
||||
value={accountName || null}
|
||||
onChange={(_, val) => setAccountName(val ?? "")}
|
||||
renderInput={(params) => (
|
||||
<TextField {...params} label="Account Name" size="small" required />
|
||||
)}
|
||||
sx={{ "& .MuiOutlinedInput-root": { height: "auto", minHeight: "2.5rem" } }}
|
||||
/>
|
||||
<TextField label="Payor Username" value={payorUsername} onChange={(e) => setPayorUsername(e.target.value)} size="small" helperText="Default: aetos" />
|
||||
|
||||
<Box sx={{ display: "flex", gap: 2 }}>
|
||||
|
||||
Reference in New Issue
Block a user