import { describe, expect, test, vi } from "vitest";
import { dimensionLabDashboardFixture } from "$lib/dashboard-seed/dimensionlab";
import { loadDashboardResponse, loadDashboardTileResponse } from "./dashboard";

describe("dashboard API route", () => {
  test("returns the ready dashboard shell without hydrating live datasources", async () => {
    const fetch = vi.spyOn(globalThis, "fetch").mockRejectedValue(
      new Error("live datasource fetch should not run for the shell response"),
    );

    const response = await loadDashboardResponse({
      refreshSeedDocument: true,
      seedIfEmpty: true,
    });

    expect(response.state).toBe("ready");
    if (response.state !== "ready") throw new Error("expected ready dashboard");
    expect(response.document.metadata.title).toBe(
      dimensionLabDashboardFixture.metadata.title,
    );
    expect(fetch).not.toHaveBeenCalled();

    fetch.mockRestore();
  });

  test("reports when client-side live hydration is disabled", async () => {
    const previous = process.env.DISABLE_LIVE_DATASOURCES;
    process.env.DISABLE_LIVE_DATASOURCES = "1";

    try {
      const response = await loadDashboardResponse({
        refreshSeedDocument: true,
        seedIfEmpty: true,
      });

      expect(response.state).toBe("ready");
      if (response.state !== "ready") throw new Error("expected ready dashboard");
      expect(response.liveDatasourceHydration).toEqual({ enabled: false });
    } finally {
      if (previous === undefined) {
        delete process.env.DISABLE_LIVE_DATASOURCES;
      } else {
        process.env.DISABLE_LIVE_DATASOURCES = previous;
      }
    }
  });

  test("hydrates a telemetry tile independently from the dashboard shell", async () => {
    const fetch = vi.fn(async (input: RequestInfo | URL) => {
      const url = String(input);

      if (url.startsWith("https://prometheus.example/api/v1/query_range")) {
        return jsonResponse({
          status: "success",
          data: {
            result: [
              {
                metric: { host: "linux-infra" },
                values: [
                  [1771430000, "10"],
                  [1771430060, "20"],
                  [1771430120, "42"],
                ],
              },
            ],
          },
        });
      }

      if (url.startsWith("https://prometheus.example/api/v1/query")) {
        return jsonResponse({
          status: "success",
          data: {
            result: [
              {
                metric: { host: "linux-infra" },
                value: [1771430400, "42"],
              },
            ],
          },
        });
      }

      throw new Error(`Unhandled test request: ${url}`);
    });

    const response = await loadDashboardTileResponse(
      { kind: "telemetry", id: "infra-ram" },
      {
        fetch,
        prometheusBaseUrl: "https://prometheus.example",
        refreshSeedDocument: true,
        seedIfEmpty: true,
      },
    );

    expect(response.state).toBe("ready");
    if (response.state !== "ready") throw new Error("expected ready tile");
    expect(response.tile).toEqual({ kind: "telemetry", id: "infra-ram" });
    expect(response.item).toMatchObject({
      id: "infra-ram",
      value: { kind: "percent", value: 42 },
      severity: "ok",
      detail: "linux-infra",
      sparkline: [10, 20, 42],
    });
    expect(fetch).toHaveBeenCalledWith(
      expect.stringContaining("/api/v1/query?"),
      expect.objectContaining({ cache: "no-store" }),
    );
    expect(fetch).toHaveBeenCalledWith(
      expect.stringContaining("/api/v1/query_range?"),
      expect.objectContaining({ cache: "no-store" }),
    );
  });

  test("hydrates a service tile with its service group identity", async () => {
    const fetch = vi.fn(async () =>
      jsonResponse({
        status: "UP",
        ping: 42,
      }),
    );

    const response = await loadDashboardTileResponse(
      { kind: "service", groupId: "essentials", id: "vaultwarden" },
      {
        fetch,
        refreshSeedDocument: true,
        seedIfEmpty: true,
      },
    );

    expect(response.state).toBe("ready");
    if (response.state !== "ready") throw new Error("expected ready tile");
    expect(response.tile).toEqual({
      kind: "service",
      groupId: "essentials",
      id: "vaultwarden",
    });
    expect(response.item).toMatchObject({
      id: "vaultwarden",
      severity: "ok",
      detail: "42 ms",
    });
  });

  test("does not hydrate tile routes when live datasources are disabled", async () => {
    const previous = process.env.DISABLE_LIVE_DATASOURCES;
    process.env.DISABLE_LIVE_DATASOURCES = "1";
    const fetch = vi.spyOn(globalThis, "fetch").mockRejectedValue(
      new Error("live datasource fetch should not run when disabled"),
    );

    try {
      const response = await loadDashboardTileResponse(
        { kind: "telemetry", id: "infra-ram" },
        {
          refreshSeedDocument: true,
          seedIfEmpty: true,
        },
      );

      expect(response.state).toBe("disabled");
      expect(fetch).not.toHaveBeenCalled();
    } finally {
      fetch.mockRestore();
      if (previous === undefined) {
        delete process.env.DISABLE_LIVE_DATASOURCES;
      } else {
        process.env.DISABLE_LIVE_DATASOURCES = previous;
      }
    }
  });
});

function jsonResponse(payload: unknown): Response {
  return new Response(JSON.stringify(payload), {
    headers: { "content-type": "application/json" },
  });
}
