Skip to content

Commit af42bfe

Browse files
committed
fix(logs): address PR review — iteration name guard, cost race, mothership retry
1 parent 8c224ba commit af42bfe

4 files changed

Lines changed: 65 additions & 56 deletions

File tree

apps/sim/app/workspace/[workspaceId]/logs/components/log-details/log-details.tsx

Lines changed: 18 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -411,22 +411,24 @@ export const LogDetails = memo(function LogDetails({
411411
<div className='flex items-center justify-between'>
412412
<h2 className='font-medium text-[var(--text-primary)] text-sm'>Log Details</h2>
413413
<div className='flex items-center gap-[1px]'>
414-
{log?.status === 'failed' && (log?.workflow?.id || log?.workflowId) && (
415-
<Tooltip.Root>
416-
<Tooltip.Trigger asChild>
417-
<Button
418-
variant='ghost'
419-
className='!p-1'
420-
onClick={() => onRetryExecution?.()}
421-
disabled={isRetryPending}
422-
aria-label='Retry execution'
423-
>
424-
<Redo className='h-[14px] w-[14px]' />
425-
</Button>
426-
</Tooltip.Trigger>
427-
<Tooltip.Content side='bottom'>Retry</Tooltip.Content>
428-
</Tooltip.Root>
429-
)}
414+
{log?.status === 'failed' &&
415+
(log?.workflow?.id || log?.workflowId) &&
416+
log?.trigger !== 'mothership' && (
417+
<Tooltip.Root>
418+
<Tooltip.Trigger asChild>
419+
<Button
420+
variant='ghost'
421+
className='!p-1'
422+
onClick={() => onRetryExecution?.()}
423+
disabled={isRetryPending}
424+
aria-label='Retry execution'
425+
>
426+
<Redo className='h-[14px] w-[14px]' />
427+
</Button>
428+
</Tooltip.Trigger>
429+
<Tooltip.Content side='bottom'>Retry</Tooltip.Content>
430+
</Tooltip.Root>
431+
)}
430432
<Button
431433
variant='ghost'
432434
className='!p-1'

apps/sim/app/workspace/[workspaceId]/logs/components/log-row-context-menu/log-row-context-menu.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,7 @@ export const LogRowContextMenu = memo(function LogRowContextMenu({
5454
const hasWorkflow = Boolean(log?.workflow?.id || log?.workflowId)
5555
const isCancellable =
5656
(log?.status === 'running' || log?.status === 'pending') && hasExecutionId && hasWorkflow
57-
const isRetryable = log?.status === 'failed' && hasWorkflow
57+
const isRetryable = log?.status === 'failed' && hasWorkflow && log?.trigger !== 'mothership'
5858

5959
return (
6060
<DropdownMenu open={isOpen} onOpenChange={(open) => !open && onClose()} modal={false}>

apps/sim/lib/logs/execution/logging-session.ts

Lines changed: 44 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -285,6 +285,46 @@ export class LoggingSession {
285285
blockType: string,
286286
output: any
287287
): Promise<void> {
288+
// Accumulate cost synchronously before any await so that fire-and-forget
289+
// callers still capture the full cost even if DB writes are not awaited.
290+
const blockOutput = output?.output
291+
if (
292+
blockOutput?.cost &&
293+
typeof blockOutput.cost.total === 'number' &&
294+
blockOutput.cost.total > 0
295+
) {
296+
const { cost, tokens, model } = blockOutput
297+
298+
this.accumulatedCost.total += cost.total || 0
299+
this.accumulatedCost.input += cost.input || 0
300+
this.accumulatedCost.output += cost.output || 0
301+
302+
if (tokens) {
303+
this.accumulatedCost.tokens.input += tokens.input || 0
304+
this.accumulatedCost.tokens.output += tokens.output || 0
305+
this.accumulatedCost.tokens.total += tokens.total || 0
306+
}
307+
308+
if (model) {
309+
if (!this.accumulatedCost.models[model]) {
310+
this.accumulatedCost.models[model] = {
311+
input: 0,
312+
output: 0,
313+
total: 0,
314+
tokens: { input: 0, output: 0, total: 0 },
315+
}
316+
}
317+
this.accumulatedCost.models[model].input += cost.input || 0
318+
this.accumulatedCost.models[model].output += cost.output || 0
319+
this.accumulatedCost.models[model].total += cost.total || 0
320+
if (tokens) {
321+
this.accumulatedCost.models[model].tokens.input += tokens.input || 0
322+
this.accumulatedCost.models[model].tokens.output += tokens.output || 0
323+
this.accumulatedCost.models[model].tokens.total += tokens.total || 0
324+
}
325+
}
326+
}
327+
288328
await this.trackProgressWrite(
289329
this.persistLastCompletedBlock({
290330
blockId,
@@ -295,47 +335,13 @@ export class LoggingSession {
295335
})
296336
)
297337

298-
const blockOutput = output?.output
299338
if (
300-
!blockOutput?.cost ||
301-
typeof blockOutput.cost.total !== 'number' ||
302-
blockOutput.cost.total <= 0
339+
blockOutput?.cost &&
340+
typeof blockOutput.cost.total === 'number' &&
341+
blockOutput.cost.total > 0
303342
) {
304-
return
343+
void this.trackProgressWrite(this.flushAccumulatedCost())
305344
}
306-
307-
const { cost, tokens, model } = blockOutput
308-
309-
this.accumulatedCost.total += cost.total || 0
310-
this.accumulatedCost.input += cost.input || 0
311-
this.accumulatedCost.output += cost.output || 0
312-
313-
if (tokens) {
314-
this.accumulatedCost.tokens.input += tokens.input || 0
315-
this.accumulatedCost.tokens.output += tokens.output || 0
316-
this.accumulatedCost.tokens.total += tokens.total || 0
317-
}
318-
319-
if (model) {
320-
if (!this.accumulatedCost.models[model]) {
321-
this.accumulatedCost.models[model] = {
322-
input: 0,
323-
output: 0,
324-
total: 0,
325-
tokens: { input: 0, output: 0, total: 0 },
326-
}
327-
}
328-
this.accumulatedCost.models[model].input += cost.input || 0
329-
this.accumulatedCost.models[model].output += cost.output || 0
330-
this.accumulatedCost.models[model].total += cost.total || 0
331-
if (tokens) {
332-
this.accumulatedCost.models[model].tokens.input += tokens.input || 0
333-
this.accumulatedCost.models[model].tokens.output += tokens.output || 0
334-
this.accumulatedCost.models[model].tokens.total += tokens.total || 0
335-
}
336-
}
337-
338-
void this.trackProgressWrite(this.flushAccumulatedCost())
339345
}
340346

341347
private async flushAccumulatedCost(): Promise<void> {

apps/sim/lib/logs/execution/trace-spans/iteration-grouping.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -226,7 +226,8 @@ function groupIterationBlocksRecursive(
226226

227227
for (const span of spans) {
228228
if (
229-
span.name.match(/^(.+) \(iteration (\d+)\)$/) ||
229+
(span.name.match(/^(.+) \(iteration (\d+)\)$/) &&
230+
(span.loopId || span.parallelId || span.blockId?.includes('_parallel_'))) ||
230231
(span.parentIterations && span.parentIterations.length > 0)
231232
) {
232233
iterationSpans.push(span)

0 commit comments

Comments
 (0)