/**
 * 店铺配送日 deliveryScheduleTimes（接口约定）
 * 1=周一 … 6=周六，7=周日
 * 示例："1,4" 周一、周四；"1,4,7" 含周日
 */
const API_WEEKDAY_I18N_KEYS: Record<number, string> = {
  1: "monday",
  2: "tuesday",
  3: "wednesday",
  4: "thursday",
  5: "friday",
  6: "saturday",
  7: "sunday",
};

/** 解析接口原始值为 API 星期数字 1–7 */
export function parseApiWeekdayNumbers(raw?: string | null): number[] {
  if (!raw || typeof raw !== "string") return [];
  const seen = new Set<number>();
  const result: number[] = [];
  raw.split(",").forEach((part) => {
    const n = Number(part.trim());
    if (Number.isInteger(n) && n >= 1 && n <= 7 && !seen.has(n)) {
      seen.add(n);
      result.push(n);
    }
  });
  return result.sort((a, b) => a - b);
}

/** API 星期 → Date.getDay()（0=周日 … 6=周六） */
export function apiWeekdayToJsDay(apiDay: number): number | null {
  if (apiDay >= 1 && apiDay <= 6) return apiDay;
  if (apiDay === 7) return 0;
  return null;
}

/** 解析为内部使用的 JS 星期（供日历可选判断） */
export function parseDeliveryScheduleTimes(
  raw?: string | null
): number[] {
  return parseApiWeekdayNumbers(raw)
    .map(apiWeekdayToJsDay)
    .filter((n): n is number => n !== null)
    .sort((a, b) => a - b);
}

export function isDeliveryScheduleDay(
  date: Date,
  schedule?: string | null | number[]
): boolean {
  const allowed = Array.isArray(schedule)
    ? schedule
    : parseDeliveryScheduleTimes(schedule);
  if (!allowed.length) return true;
  return allowed.includes(date.getDay());
}

export type MerchantAppointmentSlot = {
  date?: Date | string;
  timeSlot?: string;
  startTime: number;
  endTime: number;
};

/** 从指定日期起，找最近一天符合配送日规则的可配送日期 */
export function findNearestDeliveryScheduleDate(
  deliveryScheduleTimes?: string | null,
  fromDate: Date = new Date(),
  maxDays = 30
): Date | null {
  const base = new Date(fromDate);
  base.setHours(0, 0, 0, 0);
  for (let i = 0; i <= maxDays; i++) {
    const d = new Date(base);
    d.setDate(base.getDate() + i);
    if (isDeliveryScheduleDay(d, deliveryScheduleTimes)) {
      return d;
    }
  }
  return null;
}

/** 按自然日生成默认预约时段（全天） */
export function buildDayAppointmentSlot(date: Date): MerchantAppointmentSlot {
  const start = new Date(date);
  start.setHours(0, 0, 0, 0);
  const end = new Date(date);
  end.setHours(23, 59, 59, 999);
  return {
    date,
    timeSlot: "",
    startTime: start.getTime(),
    endTime: end.getTime(),
  };
}

/** 格式化配送日列表，用于店铺/商品详情展示 */
export function formatDeliveryScheduleDays(
  raw: string | undefined | null,
  weekdayLabel: (key: string) => string
): string {
  const apiDays = parseApiWeekdayNumbers(raw);
  if (!apiDays.length) return "";
  return apiDays
    .map((d) => {
      const key = API_WEEKDAY_I18N_KEYS[d];
      return key
        ? weekdayLabel(`pages-store.store.weekdays.${key}`)
        : "";
    })
    .filter(Boolean)
    .join("、");
}

export function buildReservationTimeUrl(options: {
  merchantId?: string | number;
  deliveryScheduleTimes?: string;
  businessHours?: string;
}): string {
  const params: string[] = [];
  if (options.merchantId != null && options.merchantId !== "") {
    params.push(`merchantId=${encodeURIComponent(String(options.merchantId))}`);
  }
  if (options.deliveryScheduleTimes) {
    params.push(
      `deliveryScheduleTimes=${encodeURIComponent(options.deliveryScheduleTimes)}`
    );
  }
  if (options.businessHours) {
    params.push(
      `storeBusinessHours=${encodeURIComponent(options.businessHours)}`
    );
  }
  const qs = params.length ? `?${params.join("&")}` : "";
  return `/pages/address/reservation-time${qs}`;
}

export const CHECKOUT_MERCHANT_APPOINTMENTS_KEY =
  "checkout_merchant_appointments";

export function saveCheckoutMerchantAppointments(
  map: Record<string, MerchantAppointmentSlot>
) {
  try {
    uni.setStorageSync(
      CHECKOUT_MERCHANT_APPOINTMENTS_KEY,
      JSON.stringify(map)
    );
  } catch {
    /* ignore */
  }
}

export function loadCheckoutMerchantAppointments(): Record<
  string,
  MerchantAppointmentSlot
> {
  try {
    const raw = uni.getStorageSync(CHECKOUT_MERCHANT_APPOINTMENTS_KEY);
    if (!raw) return {};
    const parsed = JSON.parse(String(raw));
    return parsed && typeof parsed === "object" ? parsed : {};
  } catch {
    return {};
  }
}

export function formatAppointmentPillLabel(
  slot: MerchantAppointmentSlot | undefined,
  fallback: string
): string {
  if (!slot?.startTime) return fallback;
  const start = new Date(Number(slot.startTime));
  if (Number.isNaN(start.getTime())) return fallback;
  const m = `${String(start.getMonth() + 1).padStart(2, "0")}-${String(start.getDate()).padStart(2, "0")}`;
  const weekdays = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
  return `${weekdays[start.getDay()]}, ${m.replace("-", "/")} >`;
}
