import type { Course } from '@/payload-types'

/**
 * The prices the learning platform is charging, read from it rather than kept here a second time.
 *
 * The platform is where a student actually pays, so it is the one place a price is set; this keeps the site
 * from quoting a figure the checkout does not honour. The CMS fields stay as the fallback: if the platform
 * cannot be reached the pages still print a price, and a site running with no platform beside it (a local
 * copy, a preview) works exactly as it did before.
 */
export type PlatformPrice = { cost: number; offer: number | null; offerEnds: string | null; currency: string }

type Feed = { generated: number; courses: Record<string, PlatformPrice> }

/** Where to ask. PLATFORM_INTERNAL_URL is for a server that can reach the platform on a shorter path. */
function base(): string {
  return (process.env.PLATFORM_INTERNAL_URL || process.env.PLATFORM_URL || '').trim().replace(/\/+$/, '')
}

/**
 * The prices, or null when there is no platform to ask or it did not answer.
 * Next caches the answer for five minutes, so a page render is not a round trip.
 */
export async function platformPrices(): Promise<Feed['courses'] | null> {
  const root = base()
  if (!root) return null
  try {
    const res = await fetch(`${root}/local/thinkera/prices.php`, {
      next: { revalidate: 300, tags: ['platform-prices'] },
      signal: AbortSignal.timeout(4000),
    })
    if (!res.ok) return null
    const feed = (await res.json()) as Feed
    return feed && typeof feed.courses === 'object' ? feed.courses : null
  } catch {
    // A price is not worth a broken page: the CMS values take over.
    return null
  }
}

/** The course id inside a platform address such as …/enrol/index.php?id=2 */
export function platformCourseId(href?: string | null): string | null {
  const m = (href || '').match(/[?&]id=(\d+)/)
  return m ? m[1] : null
}

/**
 * The same course list, with each course's price replaced by what the platform charges for it.
 * A course with no platform link, or one the platform does not price, is returned untouched.
 */
export async function withPlatformPrices<T extends Course>(courses: T[]): Promise<T[]> {
  const prices = await platformPrices()
  if (!prices) return courses
  return courses.map((c) => {
    const id = platformCourseId(c.platformUrl)
    const p = id ? prices[id] : undefined
    if (!p) return c
    return {
      ...c,
      price: {
        ...(c.price || {}),
        amount: p.cost,
        offer: p.offer,
        // a plain «2026-10-15» from the platform, read as that day wherever this runs
        offerEnds: p.offerEnds ? `${p.offerEnds}T00:00:00.000Z` : null,
      },
    }
  })
}
