-
-
Notifications
You must be signed in to change notification settings - Fork 724
Automatically reattempt after internal errors #1424
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
7bfaf74
e81d5bc
55cb6a9
8699d6b
0c37df7
f710326
0b39a4c
f92d82f
9350770
9f6696d
aee555a
008de3b
fc59ce2
ccda672
78ef834
cba5885
3ad51f2
3eb2f97
0839824
43085ff
8e4acc4
45a34f9
1ee3860
cb50c67
339f4ac
0921733
2e8bc83
53551e0
8111a9a
c5813c4
d3719b1
5df1807
757cc21
38f4176
f3629af
2ae2a7c
eed71f9
78a3d43
8bb7861
a2293b6
ab86276
56095a8
0e1b21c
d1c38de
cd8dffa
25a7578
6e1d4db
896edf1
d7b246e
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
--- | ||
"trigger.dev": patch | ||
"@trigger.dev/core": patch | ||
--- | ||
|
||
- Include retries.default in task retry config when indexing | ||
- New helpers for internal error retry mechanics | ||
- Detection for segfaults and ffmpeg OOM errors | ||
- Retries for packet import and export |
Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
@@ -1,15 +1,41 @@ | ||||||||||||||||||||||||||||||||||||||||||||||
import { sanitizeError, TaskRunFailedExecutionResult } from "@trigger.dev/core/v3"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { | ||||||||||||||||||||||||||||||||||||||||||||||
calculateNextRetryDelay, | ||||||||||||||||||||||||||||||||||||||||||||||
RetryOptions, | ||||||||||||||||||||||||||||||||||||||||||||||
TaskRunExecution, | ||||||||||||||||||||||||||||||||||||||||||||||
TaskRunExecutionRetry, | ||||||||||||||||||||||||||||||||||||||||||||||
TaskRunFailedExecutionResult, | ||||||||||||||||||||||||||||||||||||||||||||||
} from "@trigger.dev/core/v3"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { logger } from "~/services/logger.server"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { createExceptionPropertiesFromError, eventRepository } from "./eventRepository.server"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { BaseService } from "./services/baseService.server"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { FinalizeTaskRunService } from "./services/finalizeTaskRun.server"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { FAILABLE_RUN_STATUSES } from "./taskStatus"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { isFailableRunStatus, isFinalAttemptStatus } from "./taskStatus"; | ||||||||||||||||||||||||||||||||||||||||||||||
import type { Prisma, TaskRun } from "@trigger.dev/database"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { CompleteAttemptService } from "./services/completeAttempt.server"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { CreateTaskRunAttemptService } from "./services/createTaskRunAttempt.server"; | ||||||||||||||||||||||||||||||||||||||||||||||
import { sharedQueueTasks } from "./marqs/sharedQueueConsumer.server"; | ||||||||||||||||||||||||||||||||||||||||||||||
import * as semver from "semver"; | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const includeAttempts = { | ||||||||||||||||||||||||||||||||||||||||||||||
attempts: { | ||||||||||||||||||||||||||||||||||||||||||||||
orderBy: { | ||||||||||||||||||||||||||||||||||||||||||||||
createdAt: "desc", | ||||||||||||||||||||||||||||||||||||||||||||||
}, | ||||||||||||||||||||||||||||||||||||||||||||||
take: 1, | ||||||||||||||||||||||||||||||||||||||||||||||
}, | ||||||||||||||||||||||||||||||||||||||||||||||
lockedBy: true, // task | ||||||||||||||||||||||||||||||||||||||||||||||
lockedToVersion: true, // worker | ||||||||||||||||||||||||||||||||||||||||||||||
} satisfies Prisma.TaskRunInclude; | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
type TaskRunWithAttempts = Prisma.TaskRunGetPayload<{ | ||||||||||||||||||||||||||||||||||||||||||||||
include: typeof includeAttempts; | ||||||||||||||||||||||||||||||||||||||||||||||
}>; | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
export class FailedTaskRunService extends BaseService { | ||||||||||||||||||||||||||||||||||||||||||||||
public async call(anyRunId: string, completion: TaskRunFailedExecutionResult) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.debug("[FailedTaskRunService] Handling failed task run", { anyRunId, completion }); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const isFriendlyId = anyRunId.startsWith("run_"); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const taskRun = await this._prisma.taskRun.findUnique({ | ||||||||||||||||||||||||||||||||||||||||||||||
const taskRun = await this._prisma.taskRun.findFirst({ | ||||||||||||||||||||||||||||||||||||||||||||||
where: { | ||||||||||||||||||||||||||||||||||||||||||||||
friendlyId: isFriendlyId ? anyRunId : undefined, | ||||||||||||||||||||||||||||||||||||||||||||||
id: !isFriendlyId ? anyRunId : undefined, | ||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -25,7 +51,7 @@ export class FailedTaskRunService extends BaseService { | |||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!FAILABLE_RUN_STATUSES.includes(taskRun.status)) { | ||||||||||||||||||||||||||||||||||||||||||||||
if (!isFailableRunStatus(taskRun.status)) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.error("[FailedTaskRunService] Task run is not in a failable state", { | ||||||||||||||||||||||||||||||||||||||||||||||
taskRun, | ||||||||||||||||||||||||||||||||||||||||||||||
completion, | ||||||||||||||||||||||||||||||||||||||||||||||
|
@@ -34,33 +60,226 @@ export class FailedTaskRunService extends BaseService { | |||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
// No more retries, we need to fail the task run | ||||||||||||||||||||||||||||||||||||||||||||||
logger.debug("[FailedTaskRunService] Failing task run", { taskRun, completion }); | ||||||||||||||||||||||||||||||||||||||||||||||
const retryHelper = new FailedTaskRunRetryHelper(this._prisma); | ||||||||||||||||||||||||||||||||||||||||||||||
const retryResult = await retryHelper.call({ | ||||||||||||||||||||||||||||||||||||||||||||||
runId: taskRun.id, | ||||||||||||||||||||||||||||||||||||||||||||||
completion, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
logger.debug("[FailedTaskRunService] Completion result", { | ||||||||||||||||||||||||||||||||||||||||||||||
runId: taskRun.id, | ||||||||||||||||||||||||||||||||||||||||||||||
result: retryResult, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
interface TaskRunWithWorker extends TaskRun { | ||||||||||||||||||||||||||||||||||||||||||||||
lockedBy: { retryConfig: Prisma.JsonValue } | null; | ||||||||||||||||||||||||||||||||||||||||||||||
lockedToVersion: { sdkVersion: string } | null; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const finalizeService = new FinalizeTaskRunService(); | ||||||||||||||||||||||||||||||||||||||||||||||
await finalizeService.call({ | ||||||||||||||||||||||||||||||||||||||||||||||
id: taskRun.id, | ||||||||||||||||||||||||||||||||||||||||||||||
status: "SYSTEM_FAILURE", | ||||||||||||||||||||||||||||||||||||||||||||||
completedAt: new Date(), | ||||||||||||||||||||||||||||||||||||||||||||||
attemptStatus: "FAILED", | ||||||||||||||||||||||||||||||||||||||||||||||
error: sanitizeError(completion.error), | ||||||||||||||||||||||||||||||||||||||||||||||
export class FailedTaskRunRetryHelper extends BaseService { | ||||||||||||||||||||||||||||||||||||||||||||||
async call({ | ||||||||||||||||||||||||||||||||||||||||||||||
runId, | ||||||||||||||||||||||||||||||||||||||||||||||
completion, | ||||||||||||||||||||||||||||||||||||||||||||||
isCrash, | ||||||||||||||||||||||||||||||||||||||||||||||
}: { | ||||||||||||||||||||||||||||||||||||||||||||||
runId: string; | ||||||||||||||||||||||||||||||||||||||||||||||
completion: TaskRunFailedExecutionResult; | ||||||||||||||||||||||||||||||||||||||||||||||
isCrash?: boolean; | ||||||||||||||||||||||||||||||||||||||||||||||
}) { | ||||||||||||||||||||||||||||||||||||||||||||||
const taskRun = await this._prisma.taskRun.findFirst({ | ||||||||||||||||||||||||||||||||||||||||||||||
where: { | ||||||||||||||||||||||||||||||||||||||||||||||
id: runId, | ||||||||||||||||||||||||||||||||||||||||||||||
}, | ||||||||||||||||||||||||||||||||||||||||||||||
include: includeAttempts, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
// Now we need to "complete" the task run event/span | ||||||||||||||||||||||||||||||||||||||||||||||
await eventRepository.completeEvent(taskRun.spanId, { | ||||||||||||||||||||||||||||||||||||||||||||||
endTime: new Date(), | ||||||||||||||||||||||||||||||||||||||||||||||
attributes: { | ||||||||||||||||||||||||||||||||||||||||||||||
isError: true, | ||||||||||||||||||||||||||||||||||||||||||||||
if (!taskRun) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.error("[FailedTaskRunRetryHelper] Task run not found", { | ||||||||||||||||||||||||||||||||||||||||||||||
runId, | ||||||||||||||||||||||||||||||||||||||||||||||
completion, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return "NO_TASK_RUN"; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const retriableExecution = await this.#getRetriableAttemptExecution(taskRun, completion); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!retriableExecution) { | ||||||||||||||||||||||||||||||||||||||||||||||
return "NO_EXECUTION"; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
logger.debug("[FailedTaskRunRetryHelper] Completing attempt", { taskRun, completion }); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const executionRetry = | ||||||||||||||||||||||||||||||||||||||||||||||
completion.retry ?? | ||||||||||||||||||||||||||||||||||||||||||||||
(await FailedTaskRunRetryHelper.getExecutionRetry({ | ||||||||||||||||||||||||||||||||||||||||||||||
run: taskRun, | ||||||||||||||||||||||||||||||||||||||||||||||
execution: retriableExecution, | ||||||||||||||||||||||||||||||||||||||||||||||
})); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const completeAttempt = new CompleteAttemptService(this._prisma); | ||||||||||||||||||||||||||||||||||||||||||||||
const completeResult = await completeAttempt.call({ | ||||||||||||||||||||||||||||||||||||||||||||||
completion: { | ||||||||||||||||||||||||||||||||||||||||||||||
...completion, | ||||||||||||||||||||||||||||||||||||||||||||||
retry: executionRetry, | ||||||||||||||||||||||||||||||||||||||||||||||
}, | ||||||||||||||||||||||||||||||||||||||||||||||
events: [ | ||||||||||||||||||||||||||||||||||||||||||||||
{ | ||||||||||||||||||||||||||||||||||||||||||||||
name: "exception", | ||||||||||||||||||||||||||||||||||||||||||||||
time: new Date(), | ||||||||||||||||||||||||||||||||||||||||||||||
properties: { | ||||||||||||||||||||||||||||||||||||||||||||||
exception: createExceptionPropertiesFromError(completion.error), | ||||||||||||||||||||||||||||||||||||||||||||||
}, | ||||||||||||||||||||||||||||||||||||||||||||||
}, | ||||||||||||||||||||||||||||||||||||||||||||||
], | ||||||||||||||||||||||||||||||||||||||||||||||
execution: retriableExecution, | ||||||||||||||||||||||||||||||||||||||||||||||
isSystemFailure: !isCrash, | ||||||||||||||||||||||||||||||||||||||||||||||
isCrash, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return completeResult; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
async #getRetriableAttemptExecution( | ||||||||||||||||||||||||||||||||||||||||||||||
run: TaskRunWithAttempts, | ||||||||||||||||||||||||||||||||||||||||||||||
completion: TaskRunFailedExecutionResult | ||||||||||||||||||||||||||||||||||||||||||||||
): Promise<TaskRunExecution | undefined> { | ||||||||||||||||||||||||||||||||||||||||||||||
nicktrn marked this conversation as resolved.
Show resolved
Hide resolved
|
||||||||||||||||||||||||||||||||||||||||||||||
let attempt = run.attempts[0]; | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
// We need to create an attempt if: | ||||||||||||||||||||||||||||||||||||||||||||||
// - None exists yet | ||||||||||||||||||||||||||||||||||||||||||||||
// - The last attempt has a final status, e.g. we failed between attempts | ||||||||||||||||||||||||||||||||||||||||||||||
if (!attempt || isFinalAttemptStatus(attempt.status)) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.debug("[FailedTaskRunRetryHelper] No attempts found", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
completion, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const createAttempt = new CreateTaskRunAttemptService(this._prisma); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
try { | ||||||||||||||||||||||||||||||||||||||||||||||
const { execution } = await createAttempt.call({ | ||||||||||||||||||||||||||||||||||||||||||||||
runId: run.id, | ||||||||||||||||||||||||||||||||||||||||||||||
// This ensures we correctly respect `maxAttempts = 1` when failing before the first attempt was created | ||||||||||||||||||||||||||||||||||||||||||||||
startAtZero: true, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
return execution; | ||||||||||||||||||||||||||||||||||||||||||||||
} catch (error) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.error("[FailedTaskRunRetryHelper] Failed to create attempt", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
completion, | ||||||||||||||||||||||||||||||||||||||||||||||
error, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
// We already have an attempt with non-final status, let's use it | ||||||||||||||||||||||||||||||||||||||||||||||
try { | ||||||||||||||||||||||||||||||||||||||||||||||
const executionPayload = await sharedQueueTasks.getExecutionPayloadFromAttempt({ | ||||||||||||||||||||||||||||||||||||||||||||||
id: attempt.id, | ||||||||||||||||||||||||||||||||||||||||||||||
skipStatusChecks: true, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return executionPayload?.execution; | ||||||||||||||||||||||||||||||||||||||||||||||
} catch (error) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.error("[FailedTaskRunRetryHelper] Failed to get execution payload", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
completion, | ||||||||||||||||||||||||||||||||||||||||||||||
error, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
static async getExecutionRetry({ | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
execution, | ||||||||||||||||||||||||||||||||||||||||||||||
}: { | ||||||||||||||||||||||||||||||||||||||||||||||
run: TaskRunWithWorker; | ||||||||||||||||||||||||||||||||||||||||||||||
execution: TaskRunExecution; | ||||||||||||||||||||||||||||||||||||||||||||||
}): Promise<TaskRunExecutionRetry | undefined> { | ||||||||||||||||||||||||||||||||||||||||||||||
try { | ||||||||||||||||||||||||||||||||||||||||||||||
const retryConfig = run.lockedBy?.retryConfig; | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!retryConfig) { | ||||||||||||||||||||||||||||||||||||||||||||||
if (!run.lockedToVersion) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.error("[FailedTaskRunRetryHelper] Run not locked to version", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
execution, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const sdkVersion = run.lockedToVersion.sdkVersion ?? "0.0.0"; | ||||||||||||||||||||||||||||||||||||||||||||||
const isValid = semver.valid(sdkVersion); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!isValid) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.error("[FailedTaskRunRetryHelper] Invalid SDK version", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
execution, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
Comment on lines
+210
to
+220
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Handle potential null values for In the line where Apply this diff to safely access - const sdkVersion = run.lockedToVersion.sdkVersion ?? "0.0.0";
+ const sdkVersion = run.lockedToVersion?.sdkVersion ?? "0.0.0"; 📝 Committable suggestion
Suggested change
|
||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
// With older SDK versions, tasks only have a retry config stored in the DB if it's explicitly defined on the task itself | ||||||||||||||||||||||||||||||||||||||||||||||
// It won't get populated with retry.default in trigger.config.ts | ||||||||||||||||||||||||||||||||||||||||||||||
if (semver.lt(sdkVersion, FailedTaskRunRetryHelper.DEFAULT_RETRY_CONFIG_SINCE_VERSION)) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.warn( | ||||||||||||||||||||||||||||||||||||||||||||||
"[FailedTaskRunRetryHelper] SDK version not recent enough to determine retry config", | ||||||||||||||||||||||||||||||||||||||||||||||
{ | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
execution, | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
nicktrn marked this conversation as resolved.
Show resolved
Hide resolved
|
||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const parsedRetryConfig = RetryOptions.nullable().safeParse(retryConfig); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!parsedRetryConfig.success) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.error("[FailedTaskRunRetryHelper] Invalid retry config", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
execution, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!parsedRetryConfig.data) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.debug("[FailedTaskRunRetryHelper] No retry config", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
execution, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
const delay = calculateNextRetryDelay(parsedRetryConfig.data, execution.attempt.number); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
if (!delay) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.debug("[FailedTaskRunRetryHelper] No more retries", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
execution, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
Comment on lines
+259
to
+266
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Ensure accurate delay validation to avoid misinterpreting zero delays. Using Apply this diff to correct the condition: - if (!delay) {
+ if (delay == null) { 📝 Committable suggestion
Suggested change
|
||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return { | ||||||||||||||||||||||||||||||||||||||||||||||
timestamp: Date.now() + delay, | ||||||||||||||||||||||||||||||||||||||||||||||
delay, | ||||||||||||||||||||||||||||||||||||||||||||||
}; | ||||||||||||||||||||||||||||||||||||||||||||||
} catch (error) { | ||||||||||||||||||||||||||||||||||||||||||||||
logger.error("[FailedTaskRunRetryHelper] Failed to get execution retry", { | ||||||||||||||||||||||||||||||||||||||||||||||
run, | ||||||||||||||||||||||||||||||||||||||||||||||
execution, | ||||||||||||||||||||||||||||||||||||||||||||||
error, | ||||||||||||||||||||||||||||||||||||||||||||||
}); | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
return; | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
} | ||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||
// TODO: update this to the correct version | ||||||||||||||||||||||||||||||||||||||||||||||
static DEFAULT_RETRY_CONFIG_SINCE_VERSION = "3.0.14"; | ||||||||||||||||||||||||||||||||||||||||||||||
} |
Uh oh!
There was an error while loading. Please reload this page.