import { describe, expect, inject, it } from "vitest";
import { createGraphQLClient, graphql } from "@/tests/utils/graphql-client";

const createCategory = graphql(`
  mutation CreateCategory($code: String!, $name: String!, $parentId: ID) {
    createCategory(code: $code, name: $name, parentId: $parentId) {
      id
      code
      name
    }
  }
`);

const createCategoryIdOnly = graphql(`
  mutation CreateCategoryIdOnly($code: String!, $name: String!, $parentId: ID) {
    createCategory(code: $code, name: $name, parentId: $parentId) {
      id
    }
  }
`);

describe("product-manager--create-category", () => {
  const gql = createGraphQLClient(inject("url"), inject("token"));

  it("Given a unique code and name with no parentId, a root category is created successfully", async () => {
    const code = `CAT-${Date.now()}`;
    const result = await gql.mutation(createCategory, { code, name: "Root Category" }).toPromise();

    expect(result.data?.createCategory.code).toBe(code);
    expect(result.data?.createCategory.name).toBe("Root Category");
    expect(result.data?.createCategory.id).toBeDefined();
  });

  it("Given a unique code, name, and valid parentId, a child category is created under the specified parent", async () => {
    const parentCode = `PARENT-${Date.now()}`;
    const parentResult = await gql
      .mutation(createCategoryIdOnly, { code: parentCode, name: "Parent" })
      .toPromise();
    const parentId = parentResult.data!.createCategory.id;

    const childCode = `CHILD-${Date.now()}`;
    const result = await gql
      .mutation(createCategory, { code: childCode, name: "Child Category", parentId })
      .toPromise();

    expect(result.data?.createCategory.code).toBe(childCode);
    expect(result.data?.createCategory.name).toBe("Child Category");
  });

  it("Given a code that already exists, creation fails with a duplicate code error", async () => {
    const code = `DUP-${Date.now()}`;
    await gql.mutation(createCategoryIdOnly, { code, name: "First" }).toPromise();

    await expect(
      gql.mutation(createCategoryIdOnly, { code, name: "Second" }).toPromise(),
    ).rejects.toThrow();
  });

  it("Given a parentId that does not exist, creation fails with a parent not found error", async () => {
    const code = `ORPHAN-${Date.now()}`;
    const fakeParentId = "00000000-0000-0000-0000-000000000000";

    await expect(
      gql
        .mutation(createCategoryIdOnly, { code, name: "Orphan", parentId: fakeParentId })
        .toPromise(),
    ).rejects.toThrow();
  });
});
