// /pages/api/cron/stock_depox.js
import { db } from "@/helpers/api";
import fs from "fs";
import path from "path";

const XML_URL = "https://easy-sales.com/feed/445/975393179/okazii.xml";

const BATCH_SIZE = 100;

function writeLog(entry) {
     try {
          const logDir = path.join(process.cwd(), "logs", "cron", "stock_depox");
          fs.mkdirSync(logDir, { recursive: true });

          const date = new Date().toISOString().slice(0, 10);
          const logFile = path.join(logDir, `${date}.jsonl`);

          const line = JSON.stringify({
               time: new Date().toISOString(),
               ...entry,
          });

          fs.appendFileSync(logFile, line + "\n", "utf8");
     } catch (err) {
          console.error("[stock_depox] Eroare la scriere log:", err.message);
     }
}

function parseXML(raw) {
     const result = [];
     const auctionRegex = /<AUCTION>([\s\S]*?)<\/AUCTION>/g;
     let match;

     while ((match = auctionRegex.exec(raw)) !== null) {
          const block = match[1];

          const skuMatch = block.match(/<SKU>([^<]*)<\/SKU>/);
          const amountMatch = block.match(/<AMOUNT>([^<]*)<\/AMOUNT>/);

          if (!skuMatch || !amountMatch) continue;

          const sku = skuMatch[1].trim();
          const stock = parseInt(amountMatch[1].trim(), 10);

          if (sku && !isNaN(stock)) {
               result.push({ sku, stock });
          }
     }

     return result;
}

function chunkArray(arr, size) {
     const chunks = [];
     for (let i = 0; i < arr.length; i += size) {
          chunks.push(arr.slice(i, i + size));
     }
     return chunks;
}

async function getExistingSkus(skus) {
     const found = await db.Products.findAll({
          attributes: ["sku"],
          where: { sku: skus },
          raw: true,
     });
     return new Set(found.map((p) => p.sku));
}

function escapeSql(str) {
     return str.replace(/\\/g, "\\\\").replace(/'/g, "\\'");
}

async function updateBatch(batch) {
     if (!batch.length) return 0;

     const caseLines = batch
          .map((row) => `WHEN '${escapeSql(row.sku)}' THEN ${row.stock}`)
          .join("\n               ");

     const inList = batch
          .map((row) => `'${escapeSql(row.sku)}'`)
          .join(", ");

     const sql = `
          UPDATE products
          SET stock = CASE sku
               ${caseLines}
               ELSE stock
          END
          WHERE sku IN (${inList})
          AND back_supplier = 'DEPOX'
     `;

     const [, meta] = await db.Products.sequelize.query(sql);
     return meta?.affectedRows ?? 0;
}

export default async function handler(req, res) {
     if (req.method !== "GET" && req.method !== "POST") {
          return res.status(405).json({ error: "Method not allowed" });
     }

     // Opțional: protecție endpoint cu secret
     // const { authorization } = req.headers;
     // if (authorization !== `Bearer ${process.env.CRON_SECRET}`) {
     //      return res.status(401).json({ error: "Unauthorized" });
     // }

     if (!db.initialized) {
          await db.initialize();
     }

     const startTime = Date.now();

     try {
          const fetchResp = await fetch(XML_URL);
          if (!fetchResp.ok) {
               throw new Error(
                    `Fetch XML eșuat: ${fetchResp.status} ${fetchResp.statusText}`
               );
          }
          const rawXML = await fetchResp.text();

          const rows = parseXML(rawXML);
          if (!rows.length) {
               const entry = {
                    status: "empty_xml",
                    xml_rows: 0,
                    updated: 0,
                    not_in_site_count: 0,
                    skus_missing: [],
                    duration_ms: Date.now() - startTime,
               };
               writeLog(entry);
               return res.status(200).json(entry);
          }

          const allXmlSkus = rows.map((r) => r.sku);

          // Verificăm care SKU-uri există în DB (doar DEPOX)
          const skuChunks = chunkArray(allXmlSkus, BATCH_SIZE);
          const existingSkus = new Set();

          for (const chunk of skuChunks) {
               const found = await db.Products.findAll({
                    attributes: ["sku"],
                    where: { sku: chunk, back_supplier: "DEPOX" },
                    raw: true,
               });
               found.forEach((p) => existingSkus.add(p.sku));

               await new Promise((r) => setTimeout(r, 30));
          }

          const skusMissing = allXmlSkus.filter((s) => !existingSkus.has(s));
          const rowsToUpdate = rows.filter((r) => existingSkus.has(r.sku));

          const batches = chunkArray(rowsToUpdate, BATCH_SIZE);
          let totalUpdated = 0;

          for (let i = 0; i < batches.length; i++) {
               const affected = await updateBatch(batches[i]);
               totalUpdated += affected;

               if (i < batches.length - 1) {
                    await new Promise((r) => setTimeout(r, 50));
               }
          }

          const duration = Date.now() - startTime;

          const logEntry = {
               status: "success",
               xml_rows: rows.length,
               in_site: existingSkus.size,
               updated: totalUpdated,
               not_in_site_count: skusMissing.length,
               skus_missing: skusMissing,
               duration_ms: duration,
          };
          writeLog(logEntry);

          return res.status(200).json(logEntry);

     } catch (err) {
          console.error("[stock_depox] Eroare:", err);

          const errorEntry = {
               status: "error",
               error: err.message,
               duration_ms: Date.now() - startTime,
          };
          writeLog(errorEntry);

          return res.status(500).json(errorEntry);
     }
}