| 1 | import assert from "node:assert/strict"; |
| 2 | import { test } from "node:test"; |
| 3 | |
| 4 | import { buildError, groupBuilds } from "./deployments.ts"; |
| 5 | |
| 6 | const GIT = |
| 7 | "the commit could not be checked out: git -c failed: fatal: reference is not a tree: d2ca224ba0fea430dcc9933cda14d8aa9fa94b4b"; |
| 8 | |
| 9 | type Build = Parameters<typeof groupBuilds>[0][number] & { id: string }; |
| 10 | |
| 11 | let hour = 0; |
| 12 | const build = (over: Partial<Build>): Build => ({ |
| 13 | id: `dep_${hour}`, |
| 14 | kind: "preview", |
| 15 | branch: "v2", |
| 16 | number: 1, |
| 17 | status: "failed", |
| 18 | error: GIT, |
| 19 | createdAt: new Date(Date.parse("2026-10-07T12:00:00Z") - hour++ * 3_600_000).toISOString(), |
| 20 | ...over, |
| 21 | }); |
| 22 | |
| 23 | test("a commit that is gone is said plainly, naming the pull request", () => { |
| 24 | assert.equal( |
| 25 | buildError({ kind: "preview", number: 1, error: GIT }), |
| 26 | "This pull request's commit no longer exists. Push again, or close pull request #1.", |
| 27 | ); |
| 28 | assert.match(buildError({ kind: "production", number: null, error: GIT })!, /default branch/); |
| 29 | assert.equal(buildError({ kind: "preview", number: 1, error: "npm run build exited 1." }), "npm run build exited 1."); |
| 30 | assert.equal(buildError({ kind: "preview", number: 1, error: null }), null); |
| 31 | }); |
| 32 | |
| 33 | test("a run of the same failure of one app is one row, counted, linking to the newest", () => { |
| 34 | hour = 0; |
| 35 | const builds = [build({}), build({}), build({}), build({ status: "ready", error: null }), build({})]; |
| 36 | const groups = groupBuilds(builds); |
| 37 | assert.deepEqual( |
| 38 | groups.map((g) => [g.build.id, g.count]), |
| 39 | [ |
| 40 | ["dep_0", 3], |
| 41 | ["dep_3", 1], |
| 42 | ["dep_4", 1], |
| 43 | ], |
| 44 | ); |
| 45 | assert.equal(groups[0]!.firstAt, builds[2]!.createdAt); |
| 46 | }); |
| 47 | |
| 48 | test("other apps' builds in between do not break a run; a different error does", () => { |
| 49 | hour = 0; |
| 50 | const groups = groupBuilds([ |
| 51 | build({}), |
| 52 | build({ kind: "production", branch: null, number: null, status: "ready", error: null }), |
| 53 | build({}), |
| 54 | build({ branch: "add-ci", number: 2, error: "fatal: reference is not a tree: 213e9095" }), |
| 55 | build({}), |
| 56 | build({ error: "npm run build exited 1." }), |
| 57 | build({ error: "npm run build exited 1." }), |
| 58 | ]); |
| 59 | assert.deepEqual( |
| 60 | groups.map((g) => [g.build.id, g.count]), |
| 61 | [ |
| 62 | ["dep_0", 3], |
| 63 | ["dep_1", 1], |
| 64 | ["dep_3", 1], |
| 65 | ["dep_5", 2], |
| 66 | ], |
| 67 | ); |
| 68 | }); |
| 69 | |
| 70 | test("builds that did not fail are never folded", () => { |
| 71 | hour = 0; |
| 72 | const ready = groupBuilds([build({ status: "ready", error: null }), build({ status: "ready", error: null })]); |
| 73 | assert.deepEqual(ready.map((g) => g.count), [1, 1]); |
| 74 | assert.deepEqual(groupBuilds([]), []); |
| 75 | }); |