import type { FieldPii } from "@repo/core-shared/payload";

export type { FieldPii };

/**
 * DSR-specific Payload collection custom metadata.
 *
 * Collection authors annotate their collection configs with these shapes so the
 * DSR implementations can walk `custom.subject` linkage and filter by each
 * field's `custom.pii.exportable` flag.
 *
 * The `pii` map mirrors the field-level `FieldPii` shape from
 * `@repo/core-shared/payload` so that the `pii-declaration-must-be-complete`
 * ESLint rule is satisfied for each declared field.
 *
 * @example
 * ```ts
 * import type { DsrCollectionCustom } from "@repo/core-dsr";
 *
 * const ordersCollection: CollectionConfig = {
 *   slug: "orders",
 *   custom: {
 *     subject: { field: "userId", kind: "owner" },
 *     pii: {
 *       shippingAddress: {
 *         category: "contact-address",
 *         purpose: ["service-delivery"],
 *         exportable: true,
 *         restrictable: true,
 *       },
 *     },
 *   } satisfies DsrCollectionCustom,
 * };
 * ```
 */

export type DsrSubjectLinkKind = "self" | "owner" | "reference";

export type DsrSubjectLinkage = {
  /**
   * Field name in this collection that contains the subject's canonical ID.
   * For "self" collections (e.g. "users"), use the literal "id".
   */
  field: string;
  /**
   * - "self"      — this collection IS the subject record (e.g. users).
   * - "owner"     — the subject owns these rows (e.g. orders, blog posts).
   * - "reference" — the subject is referenced but does not own the row.
   */
  kind: DsrSubjectLinkKind;
};

/** Shape expected in `collection.custom` for DSR-enabled collections. */
export type DsrCollectionCustom = {
  /** Subject linkage metadata. Omit for collections with no subject data. */
  subject?: DsrSubjectLinkage;
  /**
   * Map of field name → FieldPii metadata. Must include all required fields
   * (`category`, `purpose`, `exportable`, `restrictable`) to satisfy the
   * `pii-declaration-must-be-complete` ESLint conformance rule.
   *
   * Omit for collections with no PII fields.
   */
  pii?: Record<string, FieldPii>;
};
