import { FastifyInstance } from "fastify";
import * as fs from "node:fs";
import * as path from "node:path";
import { fileURLToPath } from "node:url";
import type { RouteContext } from "./types.js";

/**
 * Routes pour servir les images de billes de manière sécurisée
 * Vérifie que l'utilisateur possède le skin avant de servir l'image
 */
export async function registerBallSkinImageRoutes(
  app: FastifyInstance,
  ctx: RouteContext,
) {
  const { db, requireAuth } = ctx;
  const moduleDir = path.dirname(fileURLToPath(import.meta.url));

  /**
   * GET /ball-skins/:skinId/image
   * Sert l'image d'un skin de bille si l'utilisateur le possède
   */
  app.get<{
    Params: { skinId: string };
  }>(
    "/ball-skins/:skinId/image",
    { preHandler: requireAuth },
    async (request, reply) => {
      try {
        const skinId = decodeURIComponent(request.params.skinId);

        const userId = request.user?.sub;
        if (!userId) {
          return reply.code(401).send({ error: "Authentification requise" });
        }

        // Vérifier si l'utilisateur possède ce skin
        const [rows] = await db.execute(
          "SELECT 1 FROM user_ball_skins WHERE user_id = ? AND skin_id = ? LIMIT 1",
          [userId, skinId],
        );

        if (!Array.isArray(rows) || rows.length === 0) {
          return reply.code(403).send({ error: "Skin non possédé" });
        }

        // Déterminer le chemin du fichier image
        // Format skin_id : "design_unique_1", "elementaire_5", "varie_10", etc.
        const parts = skinId.split("_");
        let category = "";
        let number = "";

        if (parts.length >= 3) {
          // Format: category_subcategory_number (ex: design_unique_1)
          category = `${parts[0]}_${parts[1]}`;
          number = parts[2];
        } else if (parts.length === 2) {
          // Format: category_number (ex: varie_1, halloween_5)
          category = parts[0];
          number = parts[1];
        } else {
          return reply.code(400).send({ error: "Format skinId invalide" });
        }

        // Mapping dossiers legacy / renommés
        // Le pack "Élémentaires" est stocké dans `elementaires/` (pluriel)
        if (category === "elementaire") {
          category = "elementaires";
        }

        const imagePath = path.join(
          moduleDir,
          "..",
          "..",
          "private",
          "ball-skins",
          category,
          `bille_${number}.png`,
        );

        if (!fs.existsSync(imagePath)) {
          return reply.code(404).send({ error: "Image introuvable" });
        }

        // Lire en mémoire pour éviter des erreurs de stream non capturées (EACCES, etc.)
        const bytes = await fs.promises.readFile(imagePath);
        reply.header("Cache-Control", "private, max-age=86400");
        reply.type("image/png");
        return reply.send(bytes);
      } catch (error) {
        request.log.error(
          { err: error, skinId: request.params.skinId },
          "ball_skin_image_failed",
        );
        return reply.code(500).send({ error: "Erreur interne" });
      }
    },
  );
}
