import { getReleasePlatformValidationSummary } from '../../src/shared/package-validation'

export type ReleasePlatformKey = 'windows' | 'macos' | 'linux'

export interface ReleaseManifestViewer {
  authenticated: boolean
  canDownload: boolean
  plan: string | null
  role: string | null
  accessStatus: string | null
}

export interface ReleaseManifestPlatformPayload {
  platform_key: ReleasePlatformKey
  platform: string
  subtitle: string
  details: string
  configured: boolean
  channel: string
  version: string | null
  build_id: string | null
  published_at: string | null
  file_name: string | null
  file_size_bytes: number | null
  checksum_sha256: string | null
  download_url: string | null
  download_available: boolean
  validation_summary: ReturnType<typeof getReleasePlatformValidationSummary>
}

export interface ReleaseManifestResponsePayload {
  ok: true
  manifest: {
    generated_at: string
    support_email: string
    public_docs_url: string | null
    release_notes_url: string | null
    corresponding_source_url: string | null
    open_source_repo_url: string | null
    commerce: {
      operator_checkout_url: string | null
      studio_checkout_url: string | null
      plan_price_operator: string
      plan_price_studio: string
    }
    viewer: ReleaseManifestViewer
    platforms: ReleaseManifestPlatformPayload[]
  }
}

type PlatformDefinition = {
  platformKey: ReleasePlatformKey
  platform: string
  subtitle: string
  details: string
  envPrefix: 'WINDOWS' | 'MACOS' | 'LINUX'
  legacyFrontendUrlKey: 'VITE_WINDOWS_DOWNLOAD_URL' | 'VITE_MAC_DOWNLOAD_URL' | 'VITE_LINUX_DOWNLOAD_URL'
}

const PLATFORM_DEFINITIONS: readonly PlatformDefinition[] = [
  {
    platformKey: 'windows',
    platform: 'Windows',
    subtitle: 'Primary shipping lane',
    details: 'Current packaged validation is strongest on the Windows Unreal lane.',
    envPrefix: 'WINDOWS',
    legacyFrontendUrlKey: 'VITE_WINDOWS_DOWNLOAD_URL',
  },
  {
    platformKey: 'macos',
    platform: 'macOS',
    subtitle: 'Planned distribution surface',
    details: 'List a signed desktop build here when the package lane is opened.',
    envPrefix: 'MACOS',
    legacyFrontendUrlKey: 'VITE_MAC_DOWNLOAD_URL',
  },
  {
    platformKey: 'linux',
    platform: 'Linux',
    subtitle: 'Operator-targeted later lane',
    details: 'Use for future package publication after the bounded release lane is widened.',
    envPrefix: 'LINUX',
    legacyFrontendUrlKey: 'VITE_LINUX_DOWNLOAD_URL',
  },
] as const

function readTrimmedEnv(env: NodeJS.ProcessEnv, ...keys: string[]) {
  for (const key of keys) {
    const value = String(env[key] || '').trim()
    if (value) {
      return value
    }
  }
  return ''
}

function readOptionalInteger(env: NodeJS.ProcessEnv, ...keys: string[]) {
  const rawValue = readTrimmedEnv(env, ...keys)
  if (!rawValue) {
    return null
  }

  const value = Number(rawValue)
  if (!Number.isFinite(value) || value < 0) {
    return null
  }

  return Math.trunc(value)
}

function readOptionalPlatformValue(env: NodeJS.ProcessEnv, definition: PlatformDefinition, suffix: string) {
  return readTrimmedEnv(env, `${definition.envPrefix}_${suffix}`)
}

function buildPlatformPayload(
  env: NodeJS.ProcessEnv,
  definition: PlatformDefinition,
  viewer: ReleaseManifestViewer,
): ReleaseManifestPlatformPayload {
  const globalVersion = readTrimmedEnv(env, 'RELEASE_MANIFEST_VERSION')
  const globalChannel = readTrimmedEnv(env, 'RELEASE_MANIFEST_CHANNEL') || 'preview'
  const downloadUrl = readTrimmedEnv(env, `${definition.envPrefix}_DOWNLOAD_URL`, definition.legacyFrontendUrlKey)
  const configured = downloadUrl.length > 0
  const downloadAvailable = configured && viewer.canDownload

  return {
    platform_key: definition.platformKey,
    platform: definition.platform,
    subtitle: definition.subtitle,
    details: definition.details,
    configured,
    channel: readOptionalPlatformValue(env, definition, 'RELEASE_CHANNEL') || globalChannel,
    version: readOptionalPlatformValue(env, definition, 'RELEASE_VERSION') || globalVersion || null,
    build_id: readOptionalPlatformValue(env, definition, 'RELEASE_BUILD_ID') || null,
    published_at: readOptionalPlatformValue(env, definition, 'RELEASE_PUBLISHED_AT') || null,
    file_name: readOptionalPlatformValue(env, definition, 'RELEASE_FILE_NAME') || null,
    file_size_bytes: readOptionalInteger(env, `${definition.envPrefix}_RELEASE_FILE_SIZE_BYTES`),
    checksum_sha256: readOptionalPlatformValue(env, definition, 'RELEASE_SHA256') || null,
    download_url: downloadAvailable ? downloadUrl : null,
    download_available: downloadAvailable,
    validation_summary: getReleasePlatformValidationSummary(definition.platformKey),
  }
}

export function createReleaseManifestResponse(
  viewer: ReleaseManifestViewer,
  env: NodeJS.ProcessEnv = process.env,
): ReleaseManifestResponsePayload {
  const operatorCheckoutUrl = readTrimmedEnv(env, 'VITE_PADDLE_CHECKOUT_URL_OPERATOR')
  const studioCheckoutUrl = readTrimmedEnv(env, 'VITE_PADDLE_CHECKOUT_URL_STUDIO')

  return {
    ok: true,
    manifest: {
      generated_at: new Date().toISOString(),
      support_email: readTrimmedEnv(env, 'SUPPORT_EMAIL', 'VITE_SUPPORT_EMAIL') || 'hello@hypertwist.app',
      public_docs_url: readTrimmedEnv(env, 'PUBLIC_DOCS_URL', 'VITE_PUBLIC_DOCS_URL') || null,
      release_notes_url: readTrimmedEnv(env, 'RELEASE_NOTES_URL', 'VITE_RELEASE_NOTES_URL') || null,
      corresponding_source_url: readTrimmedEnv(env, 'MPL_SOURCE_URL', 'VITE_MPL_SOURCE_URL') || null,
      open_source_repo_url: readTrimmedEnv(env, 'OPEN_SOURCE_REPO_URL', 'VITE_OPEN_SOURCE_REPO_URL') || null,
      commerce: {
        operator_checkout_url: operatorCheckoutUrl || null,
        studio_checkout_url: studioCheckoutUrl || null,
        plan_price_operator: readTrimmedEnv(env, 'VITE_PLAN_PRICE_OPERATOR') || 'Launch pricing via Paddle',
        plan_price_studio: readTrimmedEnv(env, 'VITE_PLAN_PRICE_STUDIO') || 'Contact for launch readiness',
      },
      viewer,
      platforms: PLATFORM_DEFINITIONS.map((definition) => buildPlatformPayload(env, definition, viewer)),
    },
  }
}
