import { describe, expect, test } from "vitest";
import type { FileTreeRow } from "@/lib/file-tree/types";
import { buildParentById, filterTopLevelDocIds, inferDropTargetDocId, isInvalidDocDrop } from "./dnd";

describe("file-tree/dnd", () => {
  test("inferDropTargetDocId", () => {
    const docRow: FileTreeRow = {
      kind: "doc",
      rowId: "doc:a",
      docId: "a",
      parentDocId: null,
      depth: 0,
      isExpanded: false,
      hasChildren: false,
      node: {} as any,
    };
    const indexRow: FileTreeRow = { kind: "index", rowId: "index:a", docId: "a", parentDocId: "a", depth: 1, node: {} as any };
    const assetRow: FileTreeRow = { kind: "asset", rowId: "asset:x", docId: "a", parentDocId: "a", depth: 1, asset: {} as any };
    expect(inferDropTargetDocId(docRow)).toBe("a");
    expect(inferDropTargetDocId(indexRow)).toBe("a");
    expect(inferDropTargetDocId(assetRow)).toBe("a");
    expect(inferDropTargetDocId(null)).toBe(null);
  });

  test("filterTopLevelDocIds removes descendants", () => {
    const parentById = buildParentById([
      { id: "a", parentId: null },
      { id: "b", parentId: "a" },
      { id: "c", parentId: "b" },
      { id: "d", parentId: null },
    ]);
    expect(filterTopLevelDocIds(["b", "a", "c", "d"], parentById)).toEqual(["a", "d"]);
    expect(filterTopLevelDocIds(["b", "c"], parentById)).toEqual(["b"]);
  });

  test("isInvalidDocDrop blocks self/descendant", () => {
    const parentById = buildParentById([
      { id: "a", parentId: null },
      { id: "b", parentId: "a" },
      { id: "c", parentId: "b" },
    ]);
    expect(isInvalidDocDrop({ sourceDocIds: ["a"], targetParentId: "a", parentById })).toBe(true);
    expect(isInvalidDocDrop({ sourceDocIds: ["a"], targetParentId: "b", parentById })).toBe(true);
    expect(isInvalidDocDrop({ sourceDocIds: ["b"], targetParentId: "a", parentById })).toBe(false);
  });
});
