import {
  type CommonReservedFields,
  type NoReservedFields,
  defaultGqlPermission,
  defaultPermission,
} from "@tailor-platform/erp-kit/core";
import { db, type TailorAnyDBField } from "@tailor-platform/sdk";
import { pipelineItem } from "./pipelineItem";
import { pipelineLabel } from "./pipelineLabel";

const builtins = () => ({
  itemId: db
    .uuid()
    .relation({
      type: "n-1",
      toward: { type: pipelineItem },
      backward: "pipelineItemLabels",
    })
    .description("ID of the item the label is attached to"),
  labelId: db
    .uuid()
    .relation({
      type: "n-1",
      toward: { type: pipelineLabel },
      backward: "pipelineItemLabels",
    })
    .description("ID of the label being attached"),
});

type ReservedFields = keyof ReturnType<typeof builtins> | CommonReservedFields;

export interface CreatePipelineItemLabelTypeParams<F extends Record<string, TailorAnyDBField>> {
  fields?: NoReservedFields<F, ReservedFields>;
}

export function createPipelineItemLabelType<const F extends Record<string, TailorAnyDBField>>(
  params: CreatePipelineItemLabelTypeParams<F> = {},
) {
  return db
    .type("PipelineItemLabel", {
      ...builtins(),
      // oxlint-disable-next-line typescript/no-unsafe-type-assertion -- mirrors erp-kit's createXxxType factories; field bag is constrained but TS can't prove F is concrete
      ...((params.fields ?? {}) as F),
      ...db.fields.timestamps(),
    })
    .description(
      "A many-to-many join record linking a PipelineItem and a PipelineLabel. Duplicate (itemId, labelId) pairs are prevented by a unique index, with a friendly duplicate check in the attach command.",
    )
    .indexes({
      fields: ["itemId", "labelId"],
      unique: true,
      name: "item_label_unique_idx",
    })
    .permission(defaultPermission)
    .gqlPermission(defaultGqlPermission);
}

export const pipelineItemLabel = createPipelineItemLabelType({});
