Files
sshkeyvault/tests/uebersicht.test.ts
T
florian.wildeandClaude Opus 5.5 ca61ca5b41 feat(uebersicht): echte Zahlen statt Beispieldaten (#026)
Kennzahlen, Hosts mit Abweichung, bald ablaufende Schluessel und letzte
Aktionen kommen aus der Datenbank; die Beispieldaten des Prototyps sind
entfernt. Befunde werden je Host und Benutzer in fester Reihenfolge
zusammengefasst, abgelaufene und noch ausgerollte Schluessel stehen in
Koralle. Anmeldungen bleiben dem Audit-Log vorbehalten, sonst
verdraengten sie auf der Uebersicht alles andere.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-12 16:33:11 +02:00

82 lines
3.6 KiB
TypeScript

import { beforeEach, describe, expect, it } from "vitest";
import { prisma } from "@/lib/db";
import { aktionEinordnen, befundZusammenfassen, uebersicht } from "@/server/queries/uebersicht";
import { protokollieren } from "@/server/services/protokoll";
import { datenbankLeeren } from "./hilfen/db";
/** Übersicht (#026): Zahlen aus der Datenbank, nie hinterlegt. */
beforeEach(async () => {
await datenbankLeeren();
});
describe("Befunde und Aktionen", () => {
it("fasst Befunde lesbar zusammen", () => {
expect(befundZusammenfassen(["UNBEKANNTER_SCHLUESSEL"])).toBe("1 unbekannter Schlüssel");
expect(befundZusammenfassen(["UNBEKANNTER_SCHLUESSEL", "UNBEKANNTER_SCHLUESSEL", "RECHTE"])).toBe(
"2 unbekannte Schlüssel · Rechte falsch",
);
});
it("ordnet Aktionen fuer die Farbe ein", () => {
expect(aktionEinordnen("authorized_keys.geschrieben", "ERFOLG")).toBe("ausgerollt");
expect(aktionEinordnen("schluessel.widerruf.eingeleitet", "ERFOLG")).toBe("widerrufen");
expect(aktionEinordnen("schluessel.erzeugt", "ERFOLG")).toBe("erstellt");
expect(aktionEinordnen("anmeldung.notfall", "VERWEIGERT")).toBe("verweigert");
});
});
describe("Kennzahlen", () => {
it("zaehlt Hosts, Schluessel, Abweichungen und Ablaeufe aus der Datenbank", async () => {
const jetzt = new Date("2026-10-12T10:00:00Z");
const tag = 86_400_000;
const a = await prisma.host.create({
data: { name: "srv-a", adresse: "10.0.0.1", driftZustand: "SYNCHRON", letzterAbgleichAm: jetzt },
});
const b = await prisma.host.create({
data: { name: "srv-b", adresse: "10.0.0.2", driftZustand: "DRIFT" },
});
await prisma.host.create({ data: { name: "srv-c", adresse: "10.0.0.3", erreichbar: false } });
await prisma.host.create({ data: { name: "srv-alt", adresse: "10.0.0.4", archiviertAm: jetzt } });
await prisma.abweichung.createMany({
data: [
{ hostId: b.id, zielbenutzer: "root", art: "UNBEKANNTER_SCHLUESSEL", fingerprint: "SHA256:x" },
{ hostId: b.id, zielbenutzer: "root", art: "RECHTE" },
{ hostId: a.id, zielbenutzer: "root", art: "RECHTE", behobenAm: jetzt },
],
});
let n = 0;
const key = (daten: Record<string, unknown>) =>
prisma.schluessel.create({
data: {
name: `k${++n}`,
slug: `k${n}`,
typ: "ED25519",
kategorie: "DIENST",
publicKey: "ssh-ed25519 AAAA",
fingerprint: `SHA256:k${n}`,
kommentar: "k",
...daten,
},
});
await key({ ablaufAm: new Date(jetzt.getTime() + 5 * tag) });
await key({ ablaufAm: new Date(jetzt.getTime() - 2 * tag) });
await key({ ablaufAm: new Date(jetzt.getTime() + 60 * tag) });
await key({ status: "WIDERRUFEN", ablaufAm: new Date(jetzt.getTime() + 1 * tag) });
await protokollieren({ akteur: "System", aktion: "abgleich", ergebnis: "ERFOLG", hostName: "srv-a" });
const u = await uebersicht(jetzt);
expect(u.kennzahlen.hosts).toEqual({ wert: 3, hinweis: "1 synchron · 1 nicht erreichbar" });
expect(u.kennzahlen.schluessel.wert).toBe(3);
expect(u.kennzahlen.abweichungen).toEqual({ wert: 2, hinweis: "auf 1 Host(s)" });
expect(u.kennzahlen.ablaufend).toEqual({ wert: 1, hinweis: "1 bereits abgelaufen" });
expect(u.mitAbweichung.map((m) => [m.host, m.befund])).toEqual([
["srv-b", "1 unbekannter Schlüssel · Rechte falsch"],
["srv-c", "nicht erreichbar"],
]);
expect(u.baldAblaufend.map((s) => s.zweck)).toEqual(["k2", "k1"]);
expect(u.letzterAbgleich).toEqual(jetzt);
expect(u.letzteAktionen[0]).toMatchObject({ art: "abgleich", benutzer: "System" });
});
});