import { promises as fs } from "fs";
import path from "path";
import { rasterizeSvgToPng } from "@/lib/generation/image-rasterize";
import { resolveLocalMediaPath } from "@/lib/storage/media-files";
import { isPubliclyReachableAppUrl } from "@/lib/env";

/** Strip cache-bust query/hash from media API URLs (e.g. ?v=assetId). */
export function stripMediaUrlQuery(url: string): string {
  return url.split("#")[0]?.split("?")[0] ?? url;
}

async function ensurePublishRasterPath(localPath: string): Promise<string> {
  if (!localPath.toLowerCase().endsWith(".svg")) {
    return localPath;
  }

  const pngPath = localPath.replace(/\.svg$/i, "-publish.png");
  try {
    await fs.access(pngPath);
    return pngPath;
  } catch {
    const converted = await rasterizeSvgToPng(localPath, pngPath);
    if (converted) return pngPath;
  }

  return localPath;
}

/** Resolve absolute filesystem path for a publishable raster image. */
export async function resolvePublishableImagePath(
  imageUrl: string | null | undefined,
): Promise<string | null> {
  if (!imageUrl?.trim()) return null;

  const localPath = resolveLocalMediaPath(stripMediaUrlQuery(imageUrl.trim()));
  if (!localPath) return null;

  try {
    await fs.access(localPath);
    return ensurePublishRasterPath(localPath);
  } catch {
    return null;
  }
}

/** LinkedIn and Facebook reject SVG — rasterize to PNG for publish. */
export async function resolvePublishableImageUrl(
  imageUrl: string | null | undefined,
  appOrigin: string,
): Promise<string | null> {
  if (!imageUrl?.trim()) return null;

  const clean = stripMediaUrlQuery(imageUrl.trim());
  const localPath = resolveLocalMediaPath(clean);

  if (localPath) {
    try {
      await fs.access(localPath);
      const rasterPath = await ensurePublishRasterPath(localPath);
      return `/api/media/${path.basename(rasterPath)}`;
    } catch {
      return null;
    }
  }

  if (clean.startsWith("data:image/svg")) {
    return null;
  }

  if (clean.startsWith("/api/media/") || clean.startsWith("http")) {
    return clean;
  }

  if (clean.startsWith("data:")) {
    return clean;
  }

  return `${appOrigin.replace(/\/$/, "")}${clean.startsWith("/") ? "" : "/"}${clean}`;
}

/** Load image bytes for direct platform upload — handles SVG via PNG conversion. */
export async function loadPublishableImageBuffer(
  imageUrl: string | null | undefined,
  appOrigin: string,
): Promise<Buffer | null> {
  const filePath = await resolvePublishableImagePath(imageUrl);
  if (filePath) {
    try {
      return await fs.readFile(filePath);
    } catch {
      return null;
    }
  }

  const resolved = await resolvePublishableImageUrl(imageUrl, appOrigin);
  if (!resolved) return null;

  if (resolved.startsWith("data:")) {
    const match = resolved.match(/^data:[^;]+;base64,(.+)$/);
    if (match?.[1]) return Buffer.from(match[1], "base64");
    return null;
  }

  try {
    const url = resolved.startsWith("http")
      ? resolved
      : `${appOrigin.replace(/\/$/, "")}${resolved}`;
    const res = await fetch(url);
    if (!res.ok) return null;
    const ct = res.headers.get("content-type") ?? "";
    if (ct.includes("svg")) return null;
    return Buffer.from(await res.arrayBuffer());
  } catch {
    return null;
  }
}

/** Human-readable reason when an image cannot attach at publish time. */
export function describeImageSkipReason(input: {
  imageUrl: string | null | undefined;
  appOrigin: string;
  platform: "linkedin" | "facebook" | "instagram";
  bufferLoaded: boolean;
}): string | null {
  if (!input.imageUrl?.trim()) {
    return "No banner image on this post.";
  }

  if (input.bufferLoaded) {
    return null;
  }

  const isSvg = input.imageUrl.toLowerCase().includes(".svg");
  const needsPublicUrl = input.platform === "instagram" || input.platform === "facebook";

  if (isSvg) {
    return "Banner is SVG only — PNG conversion failed. Regenerate the post image.";
  }

  if (needsPublicUrl && !isPubliclyReachableAppUrl(input.appOrigin)) {
    return `Image file exists locally but ${input.platform} cannot reach ${input.appOrigin}. Set NEXT_PUBLIC_APP_URL to your public HTTPS domain (e.g. ngrok or production URL).`;
  }

  return "Could not load banner image from disk for upload.";
}
