From ef6402a827df9856eb1ce5a60f23d3b371594146 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Andr=C3=A9=20Padez?= Date: Tue, 10 Mar 2026 05:32:35 +0000 Subject: [PATCH] fix pipeline stop, jobs link navigation, and seed quote stripping - Fix stop: abort poll now rejects the promise after killing the agent process - Fix jobs link: close modal before navigating, use react-router navigate - Fix seed parser: strip quotes from step input values (delete_source: "true") Co-Authored-By: Claude Opus 4.6 --- src/databases/officer_db/seed-tasks.ts | 3 ++- src/servers/api/tasks/pipeline-executor.ts | 10 +++------- .../FileBrowserApp/components/TaskRunnerModal.tsx | 10 ++++++---- 3 files changed, 11 insertions(+), 12 deletions(-) diff --git a/src/databases/officer_db/seed-tasks.ts b/src/databases/officer_db/seed-tasks.ts index cb0b3973..f59d8a1c 100644 --- a/src/databases/officer_db/seed-tasks.ts +++ b/src/databases/officer_db/seed-tasks.ts @@ -140,7 +140,8 @@ function parseFrontmatter(content: string) { // Step input entries (6 spaces) const inputMatch = line.match(/^\s{6}(\w[\w_-]*):\s*(.+)$/); if (inputMatch && inInputs) { - stepInputs[inputMatch[1]!] = inputMatch[2]!.trim(); + const raw = inputMatch[2]!.trim(); + stepInputs[inputMatch[1]!] = raw.replace(/^["'](.*)["']$/, '$1'); } } if (currentStep) { diff --git a/src/servers/api/tasks/pipeline-executor.ts b/src/servers/api/tasks/pipeline-executor.ts index 6e2541cd..6ab68286 100644 --- a/src/servers/api/tasks/pipeline-executor.ts +++ b/src/servers/api/tasks/pipeline-executor.ts @@ -124,9 +124,10 @@ async function runAgenticStep({ userId, email, username, role, taskDirName, prom // Poll for abort signal to kill the running agent const abortPoll = setInterval(() => { - if (abortSignal.aborted && cleanup) { + if (abortSignal.aborted) { clearInterval(abortPoll); - cleanup(); + cleanup?.(); + reject(new Error('Pipeline was stopped')); } }, 500); @@ -157,11 +158,6 @@ async function runAgenticStep({ userId, email, username, role, taskDirName, prom sidecar.sendPiPrompt(sessionId, prompt, randomUUID()); } - // If already aborted while setting up, kill immediately - if (abortSignal.aborted) { - clearInterval(abortPoll); - cleanup?.(); - } } catch (err) { clearInterval(abortPoll); cleanup?.(); diff --git a/src/workspaces/officerdev/src/apps/FileBrowser/FileBrowserApp/components/TaskRunnerModal.tsx b/src/workspaces/officerdev/src/apps/FileBrowser/FileBrowserApp/components/TaskRunnerModal.tsx index cb202a2c..333b55ff 100644 --- a/src/workspaces/officerdev/src/apps/FileBrowser/FileBrowserApp/components/TaskRunnerModal.tsx +++ b/src/workspaces/officerdev/src/apps/FileBrowser/FileBrowserApp/components/TaskRunnerModal.tsx @@ -1,4 +1,5 @@ import { useState, useEffect, useRef } from 'react'; +import { useNavigate } from 'react-router'; import { X, Play, Square, CircleCheck, CircleX, Copy, Check, Loader2, AlertCircle, ExternalLink } from 'lucide-react'; import { Dialog, DialogOverlay, DialogPortal } from '@/components/ui/dialog'; import * as DialogPrimitive from '@radix-ui/react-dialog'; @@ -697,13 +698,13 @@ const PipelineRunner = ({ taskDirName, context, cwd }: PipelineRunnerProps) => { )} {pipeline.jobId && ( - { onOpenChange(false); navigate(`/jobs/${pipeline.jobId}`); }} + className="flex items-center gap-1.5 text-xs text-duck-teal hover:text-duck-teal/80 transition-colors mt-1 cursor-pointer" > View in Jobs - + )} @@ -724,6 +725,7 @@ type TaskRunnerModalProps = { }; export const TaskRunnerModal = ({ open, onOpenChange, task, entryName, entryFullPath, entryType, cwd = { path: '' }, promptOverride, description, sandboxed }: TaskRunnerModalProps) => { + const navigate = useNavigate(); const { settings } = useSettings(); const taskSettings = settings.tasks; const entryRef = entryFullPath ?? entryName;