diff --git a/src/workspaces/officerdev/src/apps/Chat/background-job-prompt.ts b/src/workspaces/officerdev/src/apps/Chat/background-job-prompt.ts index 2e0c5009..59182667 100644 --- a/src/workspaces/officerdev/src/apps/Chat/background-job-prompt.ts +++ b/src/workspaces/officerdev/src/apps/Chat/background-job-prompt.ts @@ -120,5 +120,14 @@ export function buildBackgroundJobPrompt(spec: BackgroundJobSpec): string { `Do not read the output back to check it started. If it fails, the exit reaches me on its own —`, `that is the entire point of using the harness's mechanism, and checking by hand just adds noise`, `to the one case where nothing is wrong.`, + ``, + `IF IT EXITS:`, + ``, + `Say so in one line and STOP. Do not restart it. Do not diagnose why. Do not theorise about what`, + `else on the machine might have touched it.`, + ``, + `I can stop a job myself, from a button on its chip — so an exit is at least as likely to be me`, + `as it is to be a failure, and a job I stopped that comes back on its own is the opposite of a`, + `stop button. If I want it running again I will start it again.`, ].join('\n'); } diff --git a/src/workspaces/officerdev/src/apps/Chat/components/BackgroundTaskTray.tsx b/src/workspaces/officerdev/src/apps/Chat/components/BackgroundTaskTray.tsx index 79caa898..6b12b9d8 100644 --- a/src/workspaces/officerdev/src/apps/Chat/components/BackgroundTaskTray.tsx +++ b/src/workspaces/officerdev/src/apps/Chat/components/BackgroundTaskTray.tsx @@ -71,7 +71,13 @@ export const BackgroundTaskTray = ({ messages }: BackgroundTaskTrayProps) => { return (
- {open && setOpenId(null)} />} + {open && ( + setOpenId(null)} + onStop={open.status ? undefined : () => void stopTask(open.taskId)} + /> + )} {pinned.length > 0 && ( 0}> @@ -222,11 +228,13 @@ const TaskChip = ({ task, active, pinned, onClick, onTogglePin, onDismiss, onSto // ── Panel ── type TaskPanelProps = { + /** Present only while the task is running — the panel shows a real button rather than a bare glyph. */ + onStop?: () => void; task: BackgroundTask; onClose: () => void; }; -const TaskPanel = ({ task, onClose }: TaskPanelProps) => { +const TaskPanel = ({ task, onClose, onStop }: TaskPanelProps) => { const running = !task.status; const { data, isLoading } = useTaskDetail(task.taskId, running); const bodyRef = useRef(null); @@ -249,6 +257,20 @@ const TaskPanel = ({ task, onClose }: TaskPanelProps) => {
{running && } + {/* Labelled here, unlike the chip's icon-only version. The panel is where you come to decide + whether to keep something running, so the control that ends it should not be a glyph you + have to hover to identify. */} + {running && onStop && ( + + )}