| 367 | } |
| 368 | |
| 369 | export function useRetryExecution() { |
| 370 | const queryClient = useQueryClient() |
| 371 | return useMutation({ |
| 372 | mutationFn: async ({ workflowId, input }: { workflowId: string; input?: unknown }) => { |
| 373 | // boundary-raw-fetch: stream response, body is a ReadableStream consumed one chunk at a time |
| 374 | const res = await fetch(`/api/workflows/${workflowId}/execute`, { |
| 375 | method: 'POST', |
| 376 | headers: { 'Content-Type': 'application/json' }, |
| 377 | body: JSON.stringify({ input, triggerType: 'manual', stream: true }), |
| 378 | }) |
| 379 | if (!res.ok) { |
| 380 | const data = await res.json().catch(() => ({})) |
| 381 | throw new Error(data.error || 'Failed to retry execution') |
| 382 | } |
| 383 | const reader = res.body?.getReader() |
| 384 | if (reader) { |
| 385 | await reader.read() |
| 386 | reader.cancel() |
| 387 | } |
| 388 | return { started: true } |
| 389 | }, |
| 390 | onSettled: () => { |
| 391 | queryClient.invalidateQueries({ queryKey: logKeys.lists() }) |
| 392 | queryClient.invalidateQueries({ queryKey: logKeys.details() }) |
| 393 | queryClient.invalidateQueries({ queryKey: logKeys.byExecutionAll() }) |
| 394 | queryClient.invalidateQueries({ queryKey: logKeys.stats() }) |
| 395 | }, |
| 396 | }) |
| 397 | } |