import { apiGetPublic, ApiClientError } from "@/lib/api/client";
import type { ApiResponse } from "@/lib/api/types";
import { api } from "@/lib/api/client";
import type { CafeTheme } from "@/lib/cafe-theme";

export type QrResolve = {
  cafeId: string;
  cafeSlug: string;
  tableId: string;
  tableNumber: string;
  tableName: string;
  branchId: string;
  branchName: string;
  cafeName: string;
  primaryColor: string;
  logoUrl?: string | null;
  welcomeText: string;
  wifiPassword?: string | null;
  address?: string | null;
  isCleaning: boolean;
};

export type QrPublicMenuItem = {
  id: string;
  categoryId: string;
  name: string;
  nameAr?: string | null;
  nameEn?: string | null;
  description?: string | null;
  price: number;
  discountPercent: number;
  imageUrl?: string | null;
  videoUrl?: string | null;
  model3dUrl?: string | null;
  isAvailable: boolean;
};

export type QrPublicMenuCategory = {
  id: string;
  name: string;
  nameAr?: string | null;
  nameEn?: string | null;
  icon?: string | null;
  iconPresetId?: string | null;
  iconStyle?: string | null;
  imageUrl?: string | null;
  items: QrPublicMenuItem[];
};

export type QrPublicMenu = {
  cafeId: string;
  cafeName: string;
  slug: string;
  theme?: CafeTheme | null;
  categories: QrPublicMenuCategory[];
};

export type QrCartLine = {
  item: QrPublicMenuItem;
  qty: number;
  note?: string;
};

export type QrOrderPlaced = {
  orderId: string;
  orderNumber: string;
  totalAmount: number;
  itemCount: number;
  status: string;
  trackingToken: string;
};

export type QrOrderTrackStep = {
  key: string;
  labelKey: string;
  isComplete: boolean;
  isCurrent: boolean;
};

export type QrOrderTrack = {
  id: string;
  orderNumber: string;
  status: string;
  statusLabelKey: string;
  total: number;
  tableNumber?: string | null;
  createdAt: string;
  statusUpdatedAt: string;
  trackingToken: string;
  steps: QrOrderTrackStep[];
};

export async function resolveQrCode(code: string): Promise<QrResolve> {
  return apiGetPublic<QrResolve>(`/api/q/${encodeURIComponent(code)}`);
}

export async function fetchBranchPublicMenu(
  cafeId: string,
  branchId: string
): Promise<QrPublicMenu> {
  return apiGetPublic<QrPublicMenu>(
    `/api/public/${cafeId}/branches/${branchId}/menu`
  );
}

export type PublicSecurityConfig = {
  abuseProtectionEnabled: boolean;
  turnstileSiteKey: string | null;
  captchaRequired: boolean;
};

export async function fetchPublicSecurityConfig(): Promise<PublicSecurityConfig> {
  return apiGetPublic<PublicSecurityConfig>("/api/public/security-config");
}

function normalizeQrOrderPlaced(raw: QrOrderPlaced & Record<string, unknown>): QrOrderPlaced {
  const orderId = String(raw.orderId ?? raw.OrderId ?? "").trim();
  const orderNumber = String(raw.orderNumber ?? raw.OrderNumber ?? "").trim();
  const trackingToken = String(raw.trackingToken ?? raw.TrackingToken ?? "").trim();
  const totalAmount = Number(raw.totalAmount ?? raw.TotalAmount ?? 0);
  const itemCount = Number(raw.itemCount ?? raw.ItemCount ?? 0);
  const status = String(raw.status ?? raw.Status ?? "");
  return { orderId, orderNumber, totalAmount, itemCount, status, trackingToken };
}

export async function placeBranchGuestOrder(
  cafeId: string,
  branchId: string,
  body: {
    tableId: string;
    guestName?: string | null;
    guestPhone?: string | null;
    items: { menuItemId: string; quantity: number; notes?: string | null }[];
    captchaToken?: string | null;
  }
): Promise<QrOrderPlaced> {
  const { data } = await api.post<ApiResponse<QrOrderPlaced & Record<string, unknown>>>(
    `/api/public/${cafeId}/branches/${branchId}/orders`,
    body
  );
  if (!data.success || data.data === undefined) {
    throw new ApiClientError(
      data.error?.code ?? "REQUEST_FAILED",
      data.error?.message ?? "Request failed"
    );
  }
  const placed = normalizeQrOrderPlaced(data.data);
  if (!placed.orderId || !placed.trackingToken) {
    throw new ApiClientError(
      "INVALID_RESPONSE",
      "Order was placed but tracking data is missing."
    );
  }
  return placed;
}

export async function fetchOrderTrack(
  orderId: string,
  trackingToken: string
): Promise<QrOrderTrack> {
  return apiGetPublic<QrOrderTrack>(
    `/api/public/orders/${encodeURIComponent(orderId)}/track?token=${encodeURIComponent(trackingToken)}`
  );
}

export async function callWaiter(cafeId: string, tableId: string): Promise<void> {
  const { data } = await api.post<ApiResponse<null>>(
    `/api/public/${encodeURIComponent(cafeId)}/tables/${encodeURIComponent(tableId)}/call-waiter`
  );
  if (!data.success) {
    throw new ApiClientError(
      data.error?.code ?? "REQUEST_FAILED",
      data.error?.message ?? "Could not send request."
    );
  }
}
