/** Shared guest cart key used by the storefront and customer dashboard. */
export const GUEST_CART_STORAGE_KEY = 'meshkee-guest-cart'
export const GUEST_CART_URL_PARAM = 'guestCart'

export interface GuestCartItem {
  id: string
  name: string
  slug?: string
  price: number
  originalPrice?: number
  image: string | null
  quantity: number
}

function cookieDomain(): string | undefined {
  if (typeof window === 'undefined') return undefined
  const host = window.location.hostname.toLowerCase()
  if (host === 'localhost' || host === '127.0.0.1') return undefined
  const parts = host.split('.').filter(Boolean)
  if (parts.length < 2) return undefined
  return `.${parts.slice(-2).join('.')}`
}

function toCookiePayload(items: GuestCartItem[]): string {
  return JSON.stringify(
    items.map(({ id, name, slug, price, originalPrice, quantity }) => ({
      id,
      name,
      slug,
      price,
      originalPrice,
      quantity,
      image: null as string | null,
    })),
  )
}

function writeCookie(value: string) {
  const domain = cookieDomain()
  const maxAge = 60 * 60 * 24 * 30
  const encoded = encodeURIComponent(value)
  if (encoded.length > 3500) return
  let cookie = `${GUEST_CART_STORAGE_KEY}=${encoded}; path=/; max-age=${maxAge}; SameSite=Lax`
  if (domain) cookie += `; domain=${domain}`
  document.cookie = cookie
}

function readCookie(): string | null {
  if (typeof document === 'undefined') return null
  const prefix = `${GUEST_CART_STORAGE_KEY}=`
  const match = document.cookie.split('; ').find((row) => row.startsWith(prefix))
  if (!match) return null
  try {
    return decodeURIComponent(match.slice(prefix.length))
  } catch {
    return null
  }
}

function parseItems(raw: string | null): GuestCartItem[] {
  if (!raw) return []
  try {
    const parsed = JSON.parse(raw) as GuestCartItem[]
    return Array.isArray(parsed) ? parsed : []
  } catch {
    return []
  }
}

export function encodeGuestCartForUrl(items: GuestCartItem[]): string {
  const json = JSON.stringify(items)
  return btoa(unescape(encodeURIComponent(json)))
    .replace(/\+/g, '-')
    .replace(/\//g, '_')
    .replace(/=+$/, '')
}

export function decodeGuestCartFromUrl(encoded: string): GuestCartItem[] {
  try {
    const padded = encoded.replace(/-/g, '+').replace(/_/g, '/')
    const pad = padded.length % 4 === 0 ? '' : '='.repeat(4 - (padded.length % 4))
    const json = decodeURIComponent(escape(atob(padded + pad)))
    return parseItems(json)
  } catch {
    return []
  }
}

/**
 * Prefer cart payload passed from the storefront URL (cross-origin),
 * then localStorage, then shared cookie.
 */
export function loadGuestCart(): GuestCartItem[] {
  if (typeof window === 'undefined') return []

  const fromUrl = ingestGuestCartFromLocation()
  if (fromUrl.length > 0) return fromUrl

  const fromLocal = parseItems(localStorage.getItem(GUEST_CART_STORAGE_KEY))
  if (fromLocal.length > 0) return fromLocal

  return parseItems(readCookie())
}

export function ingestGuestCartFromLocation(): GuestCartItem[] {
  if (typeof window === 'undefined') return []

  const hash = window.location.hash.replace(/^#/, '')
  const search = window.location.search.replace(/^\?/, '')
  const params = new URLSearchParams(hash.includes('=') ? hash : search)
  const encoded = params.get(GUEST_CART_URL_PARAM)
  if (!encoded) return []

  const items = decodeGuestCartFromUrl(encoded)
  if (items.length === 0) return []

  saveGuestCart(items)

  // Clean the payload from the address bar
  const nextUrl = `${window.location.pathname}${window.location.search}`
  window.history.replaceState(null, '', nextUrl)

  return items
}

export function saveGuestCart(items: GuestCartItem[]) {
  if (typeof window === 'undefined') return
  const raw = JSON.stringify(items)
  localStorage.setItem(GUEST_CART_STORAGE_KEY, raw)
  try {
    writeCookie(toCookiePayload(items))
  } catch {
    // ignore cookie failures
  }
}

export function clearGuestCart() {
  if (typeof window === 'undefined') return
  localStorage.removeItem(GUEST_CART_STORAGE_KEY)
  const domain = cookieDomain()
  let cookie = `${GUEST_CART_STORAGE_KEY}=; path=/; max-age=0; SameSite=Lax`
  if (domain) cookie += `; domain=${domain}`
  document.cookie = cookie
}
