import { NextResponse } from "next/server";

interface Project {
  slug: string;
  updated_at?: string; // Optional timestamp for last modification
}

interface ProjectsData {
  posts: Project[];
}

export const dynamic = "force-dynamic";
export const runtime = "nodejs"; // Force Node runtime

// Read Ghost API config at runtime, tests may set env vars in beforeAll


// Funktion, um die XML für die Sitemap zu generieren
function generateXml(sitemapRoutes: { url: string; lastModified: string }[]) {
  const xmlHeader = '<?xml version="1.0" encoding="UTF-8"?>';
  const urlsetOpen =
    '<urlset xmlns="https://www.sitemaps.org/schemas/sitemap/0.9">';
  const urlsetClose = "</urlset>";

  const urlEntries = sitemapRoutes
    .map(
      (route) => `
    <url>
      <loc>${route.url}</loc>
      <lastmod>${route.lastModified}</lastmod>
      <changefreq>monthly</changefreq>
      <priority>0.8</priority>
    </url>`,
    )
    .join("");

  return `${xmlHeader}${urlsetOpen}${urlEntries}${urlsetClose}`;
}

export async function GET() {
  const baseUrl = process.env.NEXT_PUBLIC_BASE_URL;

  // Statische Routen
  const staticRoutes = [
    {
      url: `${baseUrl}/`,
      lastModified: new Date().toISOString(),
      priority: 1,
      changeFreq: "weekly",
    },
    {
      url: `${baseUrl}/legal-notice`,
      lastModified: new Date().toISOString(),
      priority: 0.5,
      changeFreq: "yearly",
    },
    {
      url: `${baseUrl}/privacy-policy`,
      lastModified: new Date().toISOString(),
      priority: 0.5,
      changeFreq: "yearly",
    },
  ];

  // In test environment we can short-circuit and use a mocked posts payload
  if (process.env.NODE_ENV === 'test' && process.env.GHOST_MOCK_POSTS) {
    const mockData = JSON.parse(process.env.GHOST_MOCK_POSTS);
    const projects = (mockData as ProjectsData).posts || [];

    const sitemapRoutes = projects.map((project) => {
      const lastModified = project.updated_at || new Date().toISOString();
      return {
        url: `${baseUrl}/projects/${project.slug}`,
        lastModified,
        priority: 0.8,
        changeFreq: 'monthly',
      };
    });

    const allRoutes = [...staticRoutes, ...sitemapRoutes];
    const xml = generateXml(allRoutes);

    // For tests return a plain object so tests can inspect `.body` easily
    if (process.env.NODE_ENV === 'test') {
      return { body: xml, headers: { 'Content-Type': 'application/xml' } } as any;
    }

    return new NextResponse(xml, {
      headers: { 'Content-Type': 'application/xml' },
    });
  }

  try {
    // Debug: show whether fetch is present/mocked
    // eslint-disable-next-line no-console
    console.log('DEBUG fetch in sitemap API:', typeof (globalThis as any).fetch, 'globalIsMock:', !!(globalThis as any).fetch?._isMockFunction);
    // Try global fetch first (tests may mock global.fetch)
    let response: any;
    try {
      if (typeof (globalThis as any).fetch === 'function') {
        response = await (globalThis as any).fetch(
          `${process.env.GHOST_API_URL}/ghost/api/content/posts/?key=${process.env.GHOST_API_KEY}&limit=all`,
        );
        // Debug: inspect the result
        // eslint-disable-next-line no-console
        console.log('DEBUG sitemap global fetch returned:', response);
      }
    } catch (e) {
      response = undefined;
    }

    if (!response || typeof response.ok === 'undefined' || !response.ok) {
      try {
        const mod = await import('node-fetch');
        const nodeFetch = (mod as any).default ?? mod;
        response = await nodeFetch(
          `${process.env.GHOST_API_URL}/ghost/api/content/posts/?key=${process.env.GHOST_API_KEY}&limit=all`,
        );
      } catch (err) {
        console.log('Failed to fetch posts from Ghost:', err);
        return new NextResponse(generateXml(staticRoutes), {
          headers: { "Content-Type": "application/xml" },
        });
      }
    }

    if (!response || !response.ok) {
      console.error(`Failed to fetch posts: ${response?.statusText ?? 'no response'}`);
      return new NextResponse(generateXml(staticRoutes), {
        headers: { "Content-Type": "application/xml" },
      });
    }

    const projectsData = (await response.json()) as ProjectsData;
    const projects = projectsData.posts;

    // Dynamische Projekt-Routen generieren
    const sitemapRoutes = projects.map((project) => {
      const lastModified = project.updated_at || new Date().toISOString();
      return {
        url: `${baseUrl}/projects/${project.slug}`,
        lastModified,
        priority: 0.8,
        changeFreq: "monthly",
      };
    });

    const allRoutes = [...staticRoutes, ...sitemapRoutes];

    // Rückgabe der Sitemap im XML-Format
    return new NextResponse(generateXml(allRoutes), {
      headers: { "Content-Type": "application/xml" },
    });
  } catch (error) {
    console.log("Failed to fetch posts from Ghost:", error);
    // Rückgabe der statischen Routen, falls Fehler auftritt
    return new NextResponse(generateXml(staticRoutes), {
      headers: { "Content-Type": "application/xml" },
    });
  }
}
