import multer from "multer";
import path from "path";

import type CustomRequest from "../types/requestType.js";
import { type NextFunction, type Response } from "express";
import log from "../config/log";

const storage = multer.diskStorage({
  destination: function (req: any, file: any, cb: any) {
    cb(null, "./uploads/tmp/");
  },
  filename: function (req: any, file: any, cb: any) {
    const uniqueSuffix = Date.now() + "-" + Math.round(Math.random() * 1e9);
    const fileExtension = file.mimetype.split("/")[1];
    //cb(null, `image-${uniqueSuffix}.${file.mimetype.replace("image/", "")}`);
    cb(null, `image-${uniqueSuffix}.${fileExtension}`);
  },
});

export const fileFilter = (req: any, file: any, cb: any) => {
  const allowedExtensions = [
    ".jpeg",
    ".jpg",
    ".png",
    ".webp",
    ".gif",
    ".pdf",
    ".heic",
    ".heif",
    ".xlsx",
    ".xls",
  ];

  const allowedMimeTypes = [
    "image/jpeg",
    "image/png",
    "image/webp",
    "image/gif",
    "application/pdf",
    "image/heic",
    "image/heif",
    "application/octet-stream",
    "application/vnd.ms-excel",
    "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",
  ];

  const ext = path.extname(file.originalname).toLowerCase();

  const extname = allowedExtensions.includes(ext);
  const mimetype = allowedMimeTypes.includes(file.mimetype);

  //allow if MIME is valid
  if (mimetype) {
    return cb(null, true);
  }

  log.info(
    `[Middleware], [Upload Error], originalName [${file.originalname}], extension [${ext}], mimeType [${file.mimetype}], fieldName [${file.fieldname}], EndPoint [${req.originalUrl}], Only Images and PDFs files are allowed`
  );

  return cb(new Error("Only Images and PDFs files are allowed"));
};

export const multerSingleFn = async (
  req: CustomRequest,
  res: Response,
  next: NextFunction
) => {
  const upload = multer({ storage: storage, fileFilter: fileFilter }).single("file");

  upload(req, res, function (err: any) {
    if (err) {
      log.info(
        `[Middleware], [multerSingleFn], Multer Error : ${err?.message || err}`
      );

      return res.status(400).json({
        msg: "Please check the file format or try again later.",
        isSuccess: false,
      });
    }

    next();
  });
};

// export const multerArrayFn = async (
//   req: CustomRequest,
//   res: Response,
//   next: NextFunction,
//   limit: number
// ) => {
//   const upload = multer({ storage: storage, fileFilter: fileFilter }).array("files", limit);

//   upload(req, res, function (err: any) {
//     if (err) {
//       log.info(
//         `[Middleware], [multerArrayFn], Multer Error : ${err?.message || err}`
//       );

//       return res.status(400).json({
//         msg: "Please check the file format or try again later.",
//         isSuccess: false,
//       });
//     }

//     next();
//   });
// };
export const multerArrayFn = (
  req: CustomRequest,
  res: Response,
  next: NextFunction,
  limit: number
) => {
  const upload = multer({
    storage: storage,
    fileFilter: fileFilter,
    limits: {
      files: limit
    }
  }).any();

  upload(req, res, function (err: any) {
    if (err) {
      log.info(
        `[Middleware], [multerArrayFn], Multer Error : ${err?.message || err}`
      );

      return res.status(400).json({
        msg: "Please check the file format or try again later.",
        isSuccess: false,
      });
    }

    next();
  });
};
export const multerAnyFn = async (
  req: CustomRequest,
  res: Response,
  next: NextFunction
) => {
  // Using .any() allows dynamic keys like item_0_image_0
  const upload = multer({ storage: storage, fileFilter: fileFilter }).any();

  upload(req, res, function (err: any) {
    if (err) {
      log.info(`[Middleware], [multerAnyFn], Multer Error : ${err?.message || err}`);
      return res.status(400).json({
        msg: "Please check the file format or try again later.",
        isSuccess: false,
      });
    }
    next();
  });
};
