CodeIssuesDiscussionsWikiPull RequestsProjectsCommitsActionsReleasesContributorsPulse● GatesSecuritySettingsDeploymentsPipelineInsightsAgents✨ Explain✨ Ask AI✨ Workspace✨ Spec✨ Tests▓ Debt Map✨ NL Search🏛 Archaeology
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 | /**
* Tests for src/lib/health-score.ts and src/routes/health-score.tsx.
*
* The lib is pure computation — we test scoring logic without hitting the DB.
* Route smoke tests assert 200 + HTML content-type for both read-access tiers.
*/
import { describe, test, expect } from "bun:test";
// ─── Unit tests for scoring logic ────────────────────────────────────────────
// We exercise the grade boundary and scoring helpers by reconstructing the
// formula here rather than importing (the function is async + DB-dependent).
function grade(total: number): string {
return total >= 85 ? "elite" : total >= 70 ? "strong" : total >= 50 ? "improving" : "needs-attention";
}
describe("health-score grading", () => {
test("100 → elite", () => expect(grade(100)).toBe("elite"));
test("85 → elite boundary", () => expect(grade(85)).toBe("elite"));
test("84 → strong", () => expect(grade(84)).toBe("strong"));
test("70 → strong boundary", () => expect(grade(70)).toBe("strong"));
test("69 → improving", () => expect(grade(69)).toBe("improving"));
test("50 → improving boundary", () => expect(grade(50)).toBe("improving"));
test("49 → needs-attention", () => expect(grade(49)).toBe("needs-attention"));
test("0 → needs-attention", () => expect(grade(0)).toBe("needs-attention"));
});
describe("health-score component maxima", () => {
test("security max is 30", () => {
// No advisories → full security score
const noAdv = 0;
const secScore = noAdv === 0 ? 30 : noAdv === 1 ? 20 : noAdv <= 2 ? 15 : noAdv <= 4 ? 8 : 0;
expect(secScore).toBe(30);
});
test("5+ advisories → 0 pts", () => {
const many = 5;
const secScore = many === 0 ? 30 : many === 1 ? 20 : many <= 2 ? 15 : many <= 4 ? 8 : 0;
expect(secScore).toBe(0);
});
test("gate green rate 100% → 25 pts", () => {
const rate = 1.0;
expect(Math.round(rate * 25)).toBe(25);
});
test("gate green rate 80% → ~20 pts", () => {
const rate = 0.8;
expect(Math.round(rate * 25)).toBe(20);
});
test("total max is 100 (30+25+25+20)", () => {
expect(30 + 25 + 25 + 20).toBe(100);
});
});
// ─── Route smoke tests ────────────────────────────────────────────────────────
import app from "../app";
const HAS_DB = Boolean(process.env.DATABASE_URL);
describe("GET /:owner/:repo/insights/health", () => {
test.skipIf(!HAS_DB)("non-existent repo returns 404", async () => {
const res = await app.request("/__test_owner_x__/__test_repo_x__/insights/health");
expect(res.status).toBe(404);
});
});
|