import { NextResponse } from "next/server";
import { db } from "../../../lib/db";
import { getServerSession } from "next-auth";
import { authOptions } from "../../auth/[...nextauth]/route";

export async function POST(req: Request) {
  const conn = await db.getConnection();

  try {
    await conn.beginTransaction();

    console.log("Receive POST");

    const session = await getServerSession(authOptions);

    const body = await req.json();
    console.log("Body:", body);

    const {
      id,
      quantity,
      reserved_quantity = 0,
    } = body;

    /* ================= SESSION USER (FIX UTAMA) ================= */
    const created_by = session?.user?.id
      ? Number(session.user.id)
      : null;

    /* ================= VALIDATION ================= */
    if (!id || quantity == null) {
      await conn.rollback();
      conn.release();

      return NextResponse.json(
        { message: "ID dan quantity wajib diisi" },
        { status: 400 }
      );
    }

    if (Number(quantity) < 0 || Number(reserved_quantity) < 0) {
      await conn.rollback();
      conn.release();

      return NextResponse.json(
        { message: "Quantity tidak boleh negatif" },
        { status: 400 }
      );
    }

    /* ================= FORMATTER ================= */
    const formatQty = (val: number) =>
      Number(val).toLocaleString("id-ID", {
        minimumFractionDigits: 0,
        maximumFractionDigits: 4,
      });

    /* ================= GET OLD DATA ================= */
    const [oldRows]: any = await conn.query(
      `
      SELECT 
        inv.id,
        inv.item_id,
        inv.location_id,
        inv.quantity,
        inv.reserved_quantity,
        i.name AS item_name,
        i.sku,
        l.name AS location_name
      FROM inventories inv
      JOIN items i ON i.id = inv.item_id
      JOIN locations l ON l.id = inv.location_id
      WHERE inv.id = ?
      `,
      [id]
    );

    if (oldRows.length === 0) {
      await conn.rollback();
      conn.release();

      return NextResponse.json(
        { message: "Inventory tidak ditemukan" },
        { status: 404 }
      );
    }

    const old = oldRows[0];

    /* ================= UPDATE INVENTORY ================= */
    const [result]: any = await conn.query(
      `
      UPDATE inventories
      SET
        quantity = ?,
        reserved_quantity = ?,
        updated_at = CURRENT_TIMESTAMP
      WHERE id = ?
      `,
      [quantity, reserved_quantity, id]
    );

    const deltaQty = Number(quantity) - Number(old.quantity);
    const deltaReserved =
      Number(reserved_quantity) - Number(old.reserved_quantity);

    /* ================= STOCK MOVEMENT ================= */
    if (deltaQty !== 0) {
      await conn.query(
        `
        INSERT INTO stock_movements (
          item_id,
          location_id,
          movement_type,
          quantity,
          reference_type,
          reference_id,
          notes,
          created_by
        ) VALUES (?, ?, ?, ?, ?, ?, ?, ?)
        `,
        [
          old.item_id,
          old.location_id,
          "ADJUSTMENT",
          Math.abs(deltaQty),
          "INVENTORY_UPDATE",
          id,
          `Adjust stok ${deltaQty > 0 ? "+" : ""}${formatQty(deltaQty)}: ${formatQty(old.quantity)} -> ${formatQty(Number(quantity))}`,
          created_by,
        ]
      );
    }

    /* ================= RESERVED LOG ================= */
    if (deltaReserved !== 0) {
      await conn.query(
        `
        INSERT INTO stock_movements (
          item_id,
          location_id,
          movement_type,
          quantity,
          reference_type,
          reference_id,
          notes,
          created_by
        ) VALUES (?, ?, ?, ?, ?, ?, ?, ?)
        `,
        [
          old.item_id,
          old.location_id,
          "RESERVED_ADJUSTMENT",
          Math.abs(deltaReserved),
          "INVENTORY_UPDATE",
          id,
          `Adjust reserved ${deltaReserved > 0 ? "+" : ""}${formatQty(deltaReserved)}: ${formatQty(old.reserved_quantity)} -> ${formatQty(Number(reserved_quantity))}`,
          created_by,
        ]
      );
    }

    /* ================= ACTIVITY LOG ================= */
    await conn.query(
      `
      INSERT INTO activity_logs (
        entity,
        entity_id,
        action,
        description,
        created_by
      ) VALUES (?, ?, ?, ?, ?)
      `,
      [
        "INVENTORY",
        id,
        "UPDATE",
        `Update inventory:
Item: ${old.item_name} (${old.sku})
Gudang: ${old.location_name}
Qty: ${formatQty(old.quantity)} -> ${formatQty(Number(quantity))}
Reserved: ${formatQty(old.reserved_quantity)} -> ${formatQty(Number(reserved_quantity))}
Delta Qty: ${formatQty(deltaQty)}
Delta Reserved: ${formatQty(deltaReserved)}`,
        created_by,
      ]
    );

    await conn.commit();
    conn.release();

    return NextResponse.json({
      message: "Inventory berhasil diupdate",
      affected: result.affectedRows,
    });

  } catch (err: any) {
    await conn.rollback();
    conn.release();

    console.error("ERROR UPDATE INVENTORY:", err);

    return NextResponse.json(
      {
        message: "Server error",
        error: err.message,
      },
      { status: 500 }
    );
  }
}