Skip to content

Commit 7651d9f

Browse files
authored
Bugfix start time on gantt diagram is invalid when job is retried (#26)
2 parents 666b613 + 0bb31b5 commit 7651d9f

File tree

5 files changed

+123
-14
lines changed

5 files changed

+123
-14
lines changed

dist/post.js

+18-9
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/github.ts

+12-4
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,13 @@ import { Octokit, RestEndpointMethodTypes } from "npm:@octokit/rest@19.0.13";
44
import process from "node:process";
55

66
export type Workflow =
7-
RestEndpointMethodTypes["actions"]["getWorkflowRun"]["response"]["data"];
7+
RestEndpointMethodTypes["actions"]["getWorkflowRunAttempt"]["response"][
8+
"data"
9+
];
810
export type WorkflowJobs =
9-
RestEndpointMethodTypes["actions"]["listJobsForWorkflowRun"]["response"][
11+
RestEndpointMethodTypes["actions"]["listJobsForWorkflowRunAttempt"][
12+
"response"
13+
][
1014
"data"
1115
]["jobs"];
1216

@@ -23,11 +27,13 @@ export const fetchWorkflow = async (
2327
owner: string,
2428
repo: string,
2529
runId: number,
30+
runAttempt: number,
2631
): Promise<Workflow> => {
27-
const workflow = await octokit.rest.actions.getWorkflowRun({
32+
const workflow = await octokit.rest.actions.getWorkflowRunAttempt({
2833
owner,
2934
repo,
3035
run_id: runId,
36+
attempt_number: runAttempt,
3137
});
3238
return workflow.data;
3339
};
@@ -37,11 +43,13 @@ export const fetchWorkflowRunJobs = async (
3743
owner: string,
3844
repo: string,
3945
runId: number,
46+
runAttempt: number,
4047
): Promise<WorkflowJobs> => {
41-
const workflowJob = await octokit.rest.actions.listJobsForWorkflowRun({
48+
const workflowJob = await octokit.rest.actions.listJobsForWorkflowRunAttempt({
4249
owner,
4350
repo,
4451
run_id: runId,
52+
attempt_number: runAttempt,
4553
});
4654
return workflowJob.data.jobs;
4755
};

src/post.ts

+8
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import { setTimeout } from "node:timers/promises";
2+
import process from "node:process";
23
import { debug, getInput, info, summary } from "npm:@actions/core@1.10.0";
34
import * as github from "npm:@actions/github@5.1.1";
45
import { createGantt } from "./workflow_gantt.ts";
@@ -16,11 +17,17 @@ const main = async () => {
1617
await setTimeout(1000);
1718

1819
info("Fetch workflow...");
20+
// Currently, @actions/core does not provide runAttempt.
21+
// ref: https://github.com/actions/toolkit/pull/1387
22+
const runAttempt = process.env.GITHUB_RUN_ATTEMPT
23+
? Number(process.env.GITHUB_RUN_ATTEMPT)
24+
: 1;
1925
const workflow = await fetchWorkflow(
2026
octokit,
2127
github.context.repo.owner,
2228
github.context.repo.repo,
2329
github.context.runId,
30+
runAttempt,
2431
);
2532
debug(JSON.stringify(workflow, null, 2));
2633
info("Fetch workflow_job...");
@@ -29,6 +36,7 @@ const main = async () => {
2936
github.context.repo.owner,
3037
github.context.repo.repo,
3138
github.context.runId,
39+
runAttempt,
3240
);
3341
debug(JSON.stringify(workflowJobs, null, 2));
3442

src/workflow_gantt.ts

+4-1
Original file line numberDiff line numberDiff line change
@@ -117,7 +117,10 @@ export const createGantt = (
117117
(job, jobIndex, _jobs): ganttJob => {
118118
const section = escapeName(job.name);
119119
const status: ganttStep["status"] = "active";
120-
const startJobElapsedSec = diffSec(workflow.created_at, job.created_at);
120+
const startJobElapsedSec = diffSec(
121+
workflow.run_started_at,
122+
job.created_at,
123+
);
121124
const waitingRunnerElapsedSec = diffSec(job.created_at, job.started_at);
122125
const waitingRunnerStep: ganttStep = {
123126
name: formatName("Waiting for a runner", waitingRunnerElapsedSec),

tests/workflow_gantt_test.ts

+81
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ Deno.test("1 section gantt", async (t) => {
1919
"workflow_id": 66989622,
2020
"created_at": "2023-08-25T15:57:51Z",
2121
"updated_at": "2023-08-25T15:58:19Z",
22+
"run_started_at": "2023-08-25T15:57:51Z",
2223
} as unknown as Workflow;
2324

2425
const workflowJobs = [{
@@ -133,6 +134,7 @@ ${workflowJobs[0].steps![7].name} (0s) :job0-8, after job0-7, 0s
133134
"workflow_id": 66989622,
134135
"created_at": "2023-08-25T15:57:51Z",
135136
"updated_at": "2023-08-25T15:58:19Z",
137+
"run_started_at": "2023-08-25T15:57:51Z",
136138
} as unknown as Workflow;
137139

138140
const workflowJobs = [{
@@ -210,6 +212,7 @@ ${workflowJobs[0].steps![3].name} (0s) :job0-4, after job0-3, 0s
210212
"conclusion": null,
211213
"created_at": "2023-09-24T15:41:23Z",
212214
"updated_at": "2023-09-24T15:46:01Z",
215+
"run_started_at": "2023-09-24T15:41:23Z",
213216
} as unknown as Workflow;
214217

215218
const workflowJobs = [{
@@ -279,6 +282,7 @@ ${workflowJobs[0].steps![0].name} (1s) :job0-1, after job0-0, 1s
279282
"workflow_id": 69674074,
280283
"created_at": "2023-09-25T15:55:47Z",
281284
"updated_at": "2023-09-25T15:57:36Z",
285+
"run_started_at": "2023-09-25T15:55:47Z",
282286
} as unknown as Workflow;
283287

284288
const workflowJobs = [{
@@ -339,6 +343,81 @@ ${workflowJobs[0].steps![2].name} (0s) :job0-3, after job0-2, 0s
339343
assertEquals(createGantt(workflow, workflowJobs), expect);
340344
},
341345
);
346+
347+
await t.step("retried job", () => {
348+
const workflow = {
349+
"id": 5833450919,
350+
"name": "Check self-hosted runner",
351+
"run_number": 128,
352+
"event": "workflow_dispatch",
353+
"status": "completed",
354+
"conclusion": "success",
355+
"workflow_id": 10970418,
356+
// Retried job does not changed created_at but changed run_started_at.
357+
// This dummy simulate to retry job after 1 hour.
358+
"created_at": "2023-08-11T13:00:48Z",
359+
"updated_at": "2023-08-11T14:01:56Z",
360+
"run_started_at": "2023-08-11T14:00:48Z",
361+
"run_attempt": 2,
362+
} as unknown as Workflow;
363+
364+
const workflowJobs = [
365+
{
366+
"id": 15820938470,
367+
"run_id": 5833450919,
368+
"workflow_name": "Check self-hosted runner",
369+
"status": "completed",
370+
"conclusion": "success",
371+
"created_at": "2023-08-11T14:00:50Z",
372+
"started_at": "2023-08-11T14:01:31Z",
373+
"completed_at": "2023-08-11T14:01:36Z",
374+
"name": "node",
375+
"steps": [
376+
{
377+
"name": "Set up job",
378+
"status": "completed",
379+
"conclusion": "success",
380+
"number": 1,
381+
"started_at": "2023-08-11T23:01:30.000+09:00",
382+
"completed_at": "2023-08-11T23:01:32.000+09:00",
383+
},
384+
{
385+
"name": "Set up runner",
386+
"status": "completed",
387+
"conclusion": "success",
388+
"number": 2,
389+
"started_at": "2023-08-11T23:01:32.000+09:00",
390+
"completed_at": "2023-08-11T23:01:32.000+09:00",
391+
},
392+
{
393+
"name": "Run actions/checkout@v3",
394+
"status": "completed",
395+
"conclusion": "success",
396+
"number": 3,
397+
"started_at": "2023-08-11T23:01:34.000+09:00",
398+
"completed_at": "2023-08-11T23:01:34.000+09:00",
399+
},
400+
],
401+
},
402+
] as unknown as WorkflowJobs;
403+
404+
// deno-fmt-ignore
405+
const expect = `
406+
\`\`\`mermaid
407+
gantt
408+
title ${workflowJobs[0].workflow_name}
409+
dateFormat HH:mm:ss
410+
axisFormat %H:%M:%S
411+
section ${workflowJobs[0].name}
412+
Waiting for a runner (41s) :active, job0-0, 00:00:02, 41s
413+
${workflowJobs[0].steps![0].name} (2s) :job0-1, after job0-0, 2s
414+
${workflowJobs[0].steps![1].name} (0s) :job0-2, after job0-1, 0s
415+
${workflowJobs[0].steps![2].name} (0s) :job0-3, after job0-2, 0s
416+
\`\`\`
417+
`;
418+
419+
assertEquals(createGantt(workflow, workflowJobs), expect);
420+
});
342421
});
343422

344423
Deno.test("2 section gantt", async (t) => {
@@ -353,6 +432,7 @@ Deno.test("2 section gantt", async (t) => {
353432
"workflow_id": 10970418,
354433
"created_at": "2023-08-11T14:00:48Z",
355434
"updated_at": "2023-08-11T14:01:56Z",
435+
"run_started_at": "2023-08-11T14:00:48Z",
356436
} as unknown as Workflow;
357437

358438
const workflowJobs = [
@@ -547,6 +627,7 @@ ${workflowJobs[1].steps![6].name} (0s) :job1-7, after job1-6, 0s
547627
"workflow_id": 10970418,
548628
"created_at": "2023-08-11T14:00:48Z",
549629
"updated_at": "2023-08-11T14:01:56Z",
630+
"run_started_at": "2023-08-11T14:00:48Z",
550631
} as unknown as Workflow;
551632

552633
const workflowJobs = [

0 commit comments

Comments
 (0)