import { HttpException, HttpStatus, Injectable } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { SaleDocument } from '@schemas/sale.schema';
import { ShoppingDocument } from '@schemas/shopping.schema';
import { UserDocument } from '@schemas/user.schema';
import { Model } from 'mongoose';

@Injectable()
export class InventoryService {
  constructor(
    @InjectModel('shoppings')
    private readonly shoppingModel: Model<ShoppingDocument>,
    @InjectModel('users') private userModel: Model<UserDocument>,
    @InjectModel('sales')
    private readonly saleModel: Model<SaleDocument>,
  ) {}

  async findAllEntradas(
    userId: string,
    startDate: string | null,
    endDate: string | null,
  ) {
    const user = await this.userModel.findById(userId).exec();
    if (!user) {
      throw new HttpException('Datos incorrectos', HttpStatus.CONFLICT);
    }

    const today = new Date();
    const start = startDate
      ? new Date(startDate)
      : new Date(today.setHours(0, 0, 0, 0));

    const end = endDate
      ? new Date(endDate)
      : new Date(today.setHours(23, 59, 59, 999));

    const entradas = this.shoppingModel.aggregate([
      {
        $match: {
          businessId: user.businessId,
          createdAt: {
            $gte: start,
            $lte: end,
          },
        },
      },
      { $unwind: '$products' },
      // {
      //   $lookup: {
      //     from: 'products',
      //     localField: 'products.productId',
      //     foreignField: '_id',
      //     as: 'productData',
      //   },
      // },
      // { $unwind: '$productData' },
      {
        $group: {
          _id: {
            productId: '$products.productId',
            sorteo: '$products.sorteo',
          },
          totalDotacion: { $sum: '$products.dotacion' },
        },
      },
    ]);

    console.log(entradas);
    return entradas;
  }

  async findAllDetailsEntradas(
    userId: string,
    startDate: string | null,
    endDate: string | null,
  ): Promise<any[]> {
    const user = await this.userModel.findById(userId).exec();
    if (!user) {
      throw new HttpException('Datos incorrectos', HttpStatus.CONFLICT);
    }

    const today = new Date();
    const start = startDate
      ? new Date(startDate)
      : new Date(today.setHours(0, 0, 0, 0));

    const end = endDate
      ? new Date(endDate)
      : new Date(today.setHours(23, 59, 59, 999));

    const result = await this.shoppingModel.aggregate([
      {
        $match: {
          businessId: user.businessId,
          createdAt: {
            $gte: start,
            $lte: end,
          },
        },
      },
      {
        $unwind: '$products',
      },
      /*{
        $match: {
          $or: [
            { 'products.fecha': { $gte: end } }, // los que tienen fecha válida
            { 'products.fecha': { $exists: false } }, // los que no tienen fecha
            { 'products.fecha': null }, // explícitamente nulo
          ],
        },
      },*/
      {
        $lookup: {
          from: 'products',
          localField: 'products.productId',
          foreignField: '_id',
          as: 'productDetails',
        },
      },
      {
        $unwind: '$productDetails',
      },
      {
        $match: {
          'productDetails.exists': true,
        },
      },
      {
        $group: {
          _id: {
            //identificador: '$productDetails.identificador',
            productId: '$products.productId',
            sorteo: '$products.sorteo',
          },
          identificador: { $first: '$productDetails.identificador' },
          categoria: { $first: '$productDetails.categoria' },
          clave: { $first: '$productDetails.clave' },
          totalDotacion: { $sum: '$products.dotacion' },
          totalPrecio: { $sum: '$products.precio_total' },
          totalCosto: { $sum: '$products.costo_total' },
          totalPagoAnticipado: { $sum: '$products.pago_anticipado' },
          totalSaldoPorPagar: { $sum: '$products.saldo_x_pagar' },
          totalDevolucion: { $sum: '$products.devolucion' },
          count: { $sum: 1 },
        },
      },
      {
        $sort: {
          identificador: 1,
        },
      },
    ]);

    return result;
  }

  async findAllDetailsSalidas(
    userId: string,
    startDate: string | null,
    endDate: string | null,
  ): Promise<any[]> {
    const user = await this.userModel.findById(userId).exec();
    if (!user) {
      throw new HttpException('Datos incorrectos', HttpStatus.CONFLICT);
    }

    const today = new Date();
    const start = startDate
      ? new Date(startDate)
      : new Date(today.setHours(0, 0, 0, 0));

    const end = endDate
      ? new Date(endDate)
      : new Date(today.setHours(23, 59, 59, 999));

    const result = await this.saleModel.aggregate([
      {
        $match: {
          businessId: user.businessId, // tu filtro de empresa
          cancel: { $ne: true }, // excluir canceladas
          createdAt: {
            $gte: start, // fecha inicial
            $lte: end, // fecha final
          },
        },
      },
      {
        $unwind: '$products', // descomponer los productos de cada venta
      },
      {
        $lookup: {
          from: 'products',
          localField: 'products.productId',
          foreignField: '_id',
          as: 'productDetails',
        },
      },
      {
        $unwind: '$productDetails',
      },
      {
        $match: {
          'productDetails.exists': true,
        },
      },
      {
        $group: {
          //_id: '$productDetails.identificador',
          _id: {
            productId: '$products.productId',
            sorteo: '$products.sorteo',
          },
          identificador: { $first: '$productDetails.identificador' },
          clave: { $first: '$productDetails.clave' },
          categoria: { $first: '$productDetails.categoria' },
          sorteo: { $first: '$products.sorteo' },
          totalCantidad: { $sum: '$products.cantidad' },
          totalDinero: {
            $sum: {
              $multiply: ['$products.cantidad', '$products.costo_venta'],
            },
          },
          ventas: { $sum: 1 },
        },
      },
      {
        $sort: { identificador: 1 }, // opcional: ordenar por más vendidos
      },
    ]);

    return result;
  }
}
