import type { LocaleCode } from '../i18n/messages';

export type HelpArticleSummary = {
  slug: string;
  title: string;
  summary: string;
  version_introduced?: string;
  requires_app_version?: string | null;
  status?: string;
  translation_state?: string;
  last_reviewed_at?: string;
  owner?: string;
  updated_at?: string;
  related?: Array<{ slug: string; title?: string }>;
};

export type HelpArticleDetail = HelpArticleSummary & {
  body_markdown?: string;
  body_html?: string;
  source_path?: string;
};

export interface HelpListResult {
  articles: HelpArticleSummary[];
  servedFromCache: boolean;
}

export interface HelpArticleResult {
  article: HelpArticleDetail;
  servedFromCache: boolean;
}

const AUDIENCE = 'guest';
const LIST_CACHE_TTL = 1000 * 60 * 60 * 6; // 6 hours
const DETAIL_CACHE_TTL = 1000 * 60 * 60 * 24; // 24 hours

interface CacheRecord<T> {
  storedAt: number;
  data: T;
}

function listCacheKey(locale: LocaleCode): string {
  return `help:list:${AUDIENCE}:${locale}`;
}

function detailCacheKey(locale: LocaleCode, slug: string): string {
  return `help:article:${AUDIENCE}:${locale}:${slug}`;
}

function readCache<T>(key: string, ttl: number): CacheRecord<T> | null {
  if (typeof window === 'undefined') {
    return null;
  }

  try {
    const raw = window.localStorage.getItem(key);
    if (!raw) {
      return null;
    }

    const parsed = JSON.parse(raw) as CacheRecord<T>;
    if (!parsed?.data || !parsed?.storedAt) {
      return null;
    }

    if (Date.now() - parsed.storedAt > ttl) {
      return null;
    }

    return parsed;
  } catch (error) {
    console.warn('[HelpApi] Failed to read cache', error);
    return null;
  }
}

function writeCache<T>(key: string, data: T): void {
  if (typeof window === 'undefined') {
    return;
  }
  try {
    const payload: CacheRecord<T> = {
      storedAt: Date.now(),
      data,
    };
    window.localStorage.setItem(key, JSON.stringify(payload));
  } catch (error) {
    console.warn('[HelpApi] Failed to write cache', error);
  }
}

async function requestJson<T>(url: string): Promise<T> {
  const response = await fetch(url, {
    headers: {
      'Accept': 'application/json',
    },
    credentials: 'same-origin',
  });

  if (!response.ok) {
    const error = new Error('Help request failed') as Error & { status?: number };
    error.status = response.status;
    throw error;
  }

  const payload = await response.json();
  return payload as T;
}

export async function getHelpArticles(locale: LocaleCode, options?: { forceRefresh?: boolean }): Promise<HelpListResult> {
  const cacheKey = listCacheKey(locale);
  const cached = readCache<HelpArticleSummary[]>(cacheKey, LIST_CACHE_TTL);

  if (cached && !options?.forceRefresh) {
    return { articles: cached.data, servedFromCache: true };
  }

  try {
    const params = new URLSearchParams({
      audience: AUDIENCE,
      locale,
    });
    const data = await requestJson<{ data?: HelpArticleSummary[] }>(`/api/v1/help?${params.toString()}`);
    const articles = Array.isArray(data?.data) ? data.data : [];
    writeCache(cacheKey, articles);
    return { articles, servedFromCache: false };
  } catch (error) {
    if (cached) {
      return { articles: cached.data, servedFromCache: true };
    }
    console.error('[HelpApi] Failed to fetch help articles', error);
    throw error;
  }
}

export async function getHelpArticle(slug: string, locale: LocaleCode): Promise<HelpArticleResult> {
  const cacheKey = detailCacheKey(locale, slug);
  const cached = readCache<HelpArticleDetail>(cacheKey, DETAIL_CACHE_TTL);

  if (cached) {
    return { article: cached.data, servedFromCache: true };
  }

  try {
    const params = new URLSearchParams({
      audience: AUDIENCE,
      locale,
    });
    const data = await requestJson<{ data?: HelpArticleDetail }>(`/api/v1/help/${encodeURIComponent(slug)}?${params.toString()}`);
    const article: HelpArticleDetail | undefined = data?.data;
    const safeArticle: HelpArticleDetail = article ?? { slug, title: slug, summary: '' };
    writeCache(cacheKey, safeArticle);
    return { article: safeArticle, servedFromCache: false };
  } catch (error) {
    const cachedArticle: HelpArticleDetail | undefined = (cached as { data?: HelpArticleDetail } | null | undefined)?.data;
    if (cachedArticle) {
      return { article: cachedArticle, servedFromCache: true };
    }
    console.error('[HelpApi] Failed to fetch help article', error);
    throw error;
  }
}
