ffmol-rdkit / frontend /src /App.tsx
hercules168's picture
Upload 44 files
40ad0f5 verified
Raw
History Blame Contribute Delete
2.24 kB
import { useState } from "react";
import { FlaskConical, Orbit, ShieldCheck } from "lucide-react";
import { createProjectAndRun, RankedCandidate } from "./api";
import { ProjectForm } from "./components/ProjectForm";
import { PipelineSteps } from "./components/PipelineSteps";
import { CandidateTable } from "./components/CandidateTable";
import { CandidateDetail } from "./components/CandidateDetail";
import "./styles.css";
export default function App() {
const [status, setStatus] = useState("idle");
const [error, setError] = useState<string | null>(null);
const [candidates, setCandidates] = useState<RankedCandidate[]>([]);
const selectedCandidate = candidates[0] ?? null;
async function run(payload: Record<string, string>) {
setStatus("running");
setError(null);
try {
const result = await createProjectAndRun(payload);
setStatus(result.status);
setError(result.error);
setCandidates(result.ranked_candidates ?? []);
} catch (err) {
setStatus("failed");
setError(err instanceof Error ? err.message : "Pipeline failed");
}
}
return (
<main className="app-shell">
<header className="topbar">
<div className="brand-block">
<div className="brand">
<span className="brand-mark">
<FlaskConical size={23} />
</span>
<span>Fast Follow Structure Generator</span>
</div>
<p>AI-assisted molecular optimization workbench for fast-follow discovery.</p>
</div>
<div className="topbar-signals" aria-label="Workbench safeguards">
<span>
<Orbit size={15} /> RDKit pipeline
</span>
<span>
<ShieldCheck size={15} /> Research use only
</span>
</div>
</header>
<section className="workspace">
<ProjectForm onRun={run} disabled={status === "running"} />
<PipelineSteps status={status} error={error} candidateCount={candidates.length} />
</section>
<CandidateTable candidates={candidates} />
{selectedCandidate && <CandidateDetail candidate={selectedCandidate} />}
<footer className="app-footer">powerby:海格礼斯</footer>
</main>
);
}