import { createKyselyMock } from "@tailor-platform/sdk/vitest";
import { describe, expect, it } from "vitest";
import type { Namespace } from "../generated/kysely-tailordb";
import { expectOk } from "../testing/commandTestUtils";
import { baseActiveSite, baseStockLevel } from "../testing/fixtures";
import { run } from "./getSiteStockSummary";

describe("getSiteStockSummary", () => {
  it("returns aggregated quantities per item", async () => {
    const mock = createKyselyMock<Namespace["main-db"]>();
    mock.enqueueResults([{ id: "location-1" }], [baseStockLevel]);

    const result = await run(mock.db, { siteId: baseActiveSite.id });
    const { summary } = expectOk<{
      summary: { itemId: string; totalOnHand: string }[];
    }>(result as never);

    expect(summary).toHaveLength(1);
    expect(summary[0].totalOnHand).toBe("85");
  });

  it("correctly sums across multiple locations", async () => {
    const mock = createKyselyMock<Namespace["main-db"]>();
    mock.enqueueResults(
      [{ id: "location-1" }, { id: "location-2" }],
      [
        baseStockLevel,
        {
          ...baseStockLevel,
          id: "stock-level-2",
          storageLocationId: "location-2",
          quantity: "50",
        },
        {
          ...baseStockLevel,
          id: "stock-level-3",
          storageLocationId: "location-2",
          stockType: "BLOCKED",
          quantity: "5",
        },
      ],
    );

    const result = await run(mock.db, { siteId: baseActiveSite.id });
    const { summary } = expectOk<{
      summary: {
        itemId: string;
        totalOnHand: string;
        totalReserved: string;
        totalBlocked: string;
        totalAvailable: string;
      }[];
    }>(result as never);

    expect(summary).toHaveLength(1);
    expect(summary[0].totalOnHand).toBe("140");
    expect(summary[0].totalReserved).toBe("0");
    expect(summary[0].totalBlocked).toBe("5");
  });

  it("filters by item when provided", async () => {
    const mock = createKyselyMock<Namespace["main-db"]>();
    mock.enqueueResults([{ id: "location-1" }], [baseStockLevel]);

    const result = await run(mock.db, { siteId: baseActiveSite.id, itemId: "item-1" });
    const { summary } = expectOk<{
      summary: { itemId: string; totalOnHand: string }[];
    }>(result as never);

    expect(summary).toHaveLength(1);
    expect(summary[0].itemId).toBe("item-1");
  });

  it("returns empty summary when site has no active locations", async () => {
    const mock = createKyselyMock<Namespace["main-db"]>();
    mock.enqueueResults([]);

    const result = await run(mock.db, { siteId: "nonexistent-site" });
    const { summary } = expectOk<{ summary: unknown[] }>(result as never);

    expect(summary).toEqual([]);
  });
});
