Added error from the run attempt with nice display (#1249)
This commit is contained in:
@@ -1,9 +1,9 @@
|
||||
import { Context, MachinePresetName, prettyPrintPacket } from "@trigger.dev/core/v3";
|
||||
import { MachinePresetName, prettyPrintPacket, TaskRunError } from "@trigger.dev/core/v3";
|
||||
import { FINISHED_STATUSES, RUNNING_STATUSES } from "~/components/runs/v3/TaskRunStatus";
|
||||
import { eventRepository } from "~/v3/eventRepository.server";
|
||||
import { BasePresenter } from "./basePresenter.server";
|
||||
import { machineDefinition } from "@trigger.dev/platform/v3";
|
||||
import { machinePresetFromName } from "~/v3/machinePresets.server";
|
||||
import { FINAL_ATTEMPT_STATUSES } from "~/v3/taskStatus";
|
||||
import { BasePresenter } from "./basePresenter.server";
|
||||
|
||||
type Result = Awaited<ReturnType<SpanPresenter["call"]>>;
|
||||
export type Span = NonNullable<NonNullable<Result>["span"]>;
|
||||
@@ -57,6 +57,7 @@ export class SpanPresenter extends BasePresenter {
|
||||
async getRun(spanId: string) {
|
||||
const run = await this._replica.taskRun.findFirst({
|
||||
select: {
|
||||
id: true,
|
||||
traceId: true,
|
||||
//metadata
|
||||
number: true,
|
||||
@@ -113,17 +114,6 @@ export class SpanPresenter extends BasePresenter {
|
||||
payload: true,
|
||||
payloadType: true,
|
||||
maxAttempts: true,
|
||||
//finished attempt
|
||||
attempts: {
|
||||
select: {
|
||||
output: true,
|
||||
outputType: true,
|
||||
error: true,
|
||||
},
|
||||
where: {
|
||||
status: "COMPLETED",
|
||||
},
|
||||
},
|
||||
project: {
|
||||
include: {
|
||||
organization: true,
|
||||
@@ -145,9 +135,23 @@ export class SpanPresenter extends BasePresenter {
|
||||
return;
|
||||
}
|
||||
|
||||
const finishedAttempt = run.attempts.at(0);
|
||||
const finishedAttempt = await this._replica.taskRunAttempt.findFirst({
|
||||
select: {
|
||||
output: true,
|
||||
outputType: true,
|
||||
error: true,
|
||||
},
|
||||
where: {
|
||||
status: { in: FINAL_ATTEMPT_STATUSES },
|
||||
taskRunId: run.id,
|
||||
},
|
||||
orderBy: {
|
||||
createdAt: "desc",
|
||||
},
|
||||
});
|
||||
|
||||
const output =
|
||||
finishedAttempt === undefined
|
||||
finishedAttempt === null
|
||||
? undefined
|
||||
: finishedAttempt.outputType === "application/store"
|
||||
? `/resources/packets/${run.runtimeEnvironment.id}/${finishedAttempt.output}`
|
||||
@@ -162,6 +166,19 @@ export class SpanPresenter extends BasePresenter {
|
||||
? await prettyPrintPacket(run.payload, run.payloadType ?? undefined)
|
||||
: undefined;
|
||||
|
||||
let error: TaskRunError | undefined = undefined;
|
||||
if (finishedAttempt?.error) {
|
||||
const result = TaskRunError.safeParse(finishedAttempt.error);
|
||||
if (result.success) {
|
||||
error = result.data;
|
||||
} else {
|
||||
error = {
|
||||
type: "CUSTOM_ERROR",
|
||||
raw: JSON.stringify(finishedAttempt.error),
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
const span = await eventRepository.getSpan(spanId, run.traceId);
|
||||
|
||||
const context = {
|
||||
@@ -247,8 +264,8 @@ export class SpanPresenter extends BasePresenter {
|
||||
payloadType: run.payloadType,
|
||||
output,
|
||||
outputType: finishedAttempt?.outputType ?? "application/json",
|
||||
error,
|
||||
links: span?.links,
|
||||
events: span?.events,
|
||||
context: JSON.stringify(context, null, 2),
|
||||
};
|
||||
}
|
||||
|
||||
+41
-3
@@ -5,6 +5,7 @@ import {
|
||||
formatDuration,
|
||||
formatDurationMilliseconds,
|
||||
nanosecondsToMilliseconds,
|
||||
TaskRunError,
|
||||
} from "@trigger.dev/core/v3";
|
||||
import { ReactNode, useEffect } from "react";
|
||||
import { typedjson, useTypedFetcher } from "remix-typedjson";
|
||||
@@ -12,8 +13,9 @@ import { ExitIcon } from "~/assets/icons/ExitIcon";
|
||||
import { CodeBlock } from "~/components/code/CodeBlock";
|
||||
import { EnvironmentLabel } from "~/components/environments/EnvironmentLabel";
|
||||
import { Button, LinkButton } from "~/components/primitives/Buttons";
|
||||
import { Callout } from "~/components/primitives/Callout";
|
||||
import { DateTime, DateTimeAccurate } from "~/components/primitives/DateTime";
|
||||
import { Header2 } from "~/components/primitives/Headers";
|
||||
import { Header2, Header3 } from "~/components/primitives/Headers";
|
||||
import { Paragraph } from "~/components/primitives/Paragraph";
|
||||
import * as Property from "~/components/primitives/PropertyTable";
|
||||
import { Spinner } from "~/components/primitives/Spinner";
|
||||
@@ -606,8 +608,8 @@ function RunBody({
|
||||
{run.payload !== undefined && (
|
||||
<PacketDisplay data={run.payload} dataType={run.payloadType} title="Payload" />
|
||||
)}
|
||||
{run.events !== undefined && run.events.length > 0 ? (
|
||||
<SpanEvents spanEvents={run.events} />
|
||||
{run.error !== undefined ? (
|
||||
<RunError error={run.error} />
|
||||
) : run.output !== undefined ? (
|
||||
<PacketDisplay data={run.output} dataType={run.outputType} title="Output" />
|
||||
) : null}
|
||||
@@ -791,6 +793,42 @@ function RunTimelineLine({ title, state }: RunTimelineLineProps) {
|
||||
);
|
||||
}
|
||||
|
||||
function RunError({ error }: { error: TaskRunError }) {
|
||||
switch (error.type) {
|
||||
case "STRING_ERROR":
|
||||
case "CUSTOM_ERROR": {
|
||||
return (
|
||||
<div className="flex flex-col gap-2 rounded-sm border border-rose-500/50 px-3 pb-3 pt-2">
|
||||
<CodeBlock
|
||||
showCopyButton={false}
|
||||
showLineNumbers={false}
|
||||
code={error.raw}
|
||||
maxLines={20}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
case "BUILT_IN_ERROR":
|
||||
case "INTERNAL_ERROR": {
|
||||
const name = "name" in error ? error.name : error.code;
|
||||
return (
|
||||
<div className="flex flex-col gap-2 rounded-sm border border-rose-500/50 px-3 pb-3 pt-2">
|
||||
<Header3 className="text-rose-500">{name}</Header3>
|
||||
{error.message && <Callout variant="error">{error.message}</Callout>}
|
||||
{error.stackTrace && (
|
||||
<CodeBlock
|
||||
showCopyButton={false}
|
||||
showLineNumbers={false}
|
||||
code={error.stackTrace}
|
||||
maxLines={20}
|
||||
/>
|
||||
)}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function PacketDisplay({
|
||||
data,
|
||||
dataType,
|
||||
|
||||
Reference in New Issue
Block a user