import moment from "moment";
import CONSTANTS from "../../config/constants";
import complaintDB from "../../models/complaint.model";
import duesDB from "../../models/dues.model";
import flatDB from "../../models/flat.model";
import propertyDB from "../../models/property.model";
import propertiesTypes from "../../schemas/property.schema";
import log from "../../config/log";
import tenantDB from "../../models/tenant.model";
import documentDB from "../../models/document.model";
import hiddenDuesDB from "../../models/hiddenDues.model";

export const duesForClient = async (
  clientId: number,
  propId: number,
  tenantId: number,
  pageNum: number,
  limit: number,
  date: string,
  filter: string
) => {
  let totalDuesAmt = 0;
  let totalDueTenantCount = 0;
  let overDuesAmt = 0;
  let totalDuesForCurrentMonthAmt = 0;
  let totalRentDuesAmt = 0;
  let month = moment().format("M");
  let year = moment().format("YYYY");
  let duesList = [];

  if (propId) {
    //const { totalDues } = await duesDB.getTotalDuesByPropId({ propId, dueDate: date });
    const { totalDues } = await duesDB.getTotalDuesByPropId({ propId });
    const { overDues } = await duesDB.getTotalOverduesDuesByPropId({
      propId,
      year,
      month,
    });
    const { duesForMonth } = await duesDB.getTotalDuesByPropIdYearMonth({
      propId,
      year,
      month,
    });
    const { rentDuesByType } = await duesDB.getTotalDuesByTypeByPropId({
      propId,
      type: CONSTANTS.DUES_TYPES.RENT,
      year,
      month,
    });

    const { dueTenantCount } = await duesDB.getTenantCountByPropId({
      propId,
    });
    let dues = [];
    if (filter === "1") {
      dues = await duesDB.getAllByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
      });
    } else if (filter === "2") {
      //Overdues
      dues = await duesDB.getOverdueByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        year,
        month,
      });
    } else if (filter === "3") {
      //Jan Dues
      dues = await duesDB.getByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
      });
    } else {
      // Jan Rent Dues
      dues = await duesDB.getDueByTypeByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        type: CONSTANTS.DUES_TYPES.RENT,
        dueDate: date,
      });
    }

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
    overDuesAmt = overDues;
    totalDuesForCurrentMonthAmt = duesForMonth;
    totalRentDuesAmt = rentDuesByType;
  } else if (tenantId) {
    const { totalDues } = await duesDB.getTotalDuesByTenantId({
      tenantId,
      propId,
      date,
    });
    const { dueTenantCount } = await duesDB.getTenantCountByTenantId({
      tenantId,
      date,
    });
    const dues = await duesDB.getByTenantIdandPage({
      tenantId,
      pageNum: Number(pageNum),
      limit,
      date,
    });

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
  } else {
    const { totalDues } = await duesDB.getTotalDuesByClientId({
      clientId,
      dueDate: date,
    });
    const { overDues } = await duesDB.getTotalOverduesByClientId({
      clientId,
      year,
      month,
    });
    const { duesForMonth } = await duesDB.getDuesByMonth({
      clientId,
      year,
      month,
    });
    const { rentDuesByType } = await duesDB.getTotalDuesByType({
      clientId,
      type: CONSTANTS.DUES_TYPES.RENT,
      year,
      month,
    });
    const { dueTenantCount } = await duesDB.getTenantCount({ clientId, date }); //Not Being User Sukhbir 16th Feb 2025

    let dues = [];
    if (filter === "1") {
      dues = await duesDB.getAllByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
      });
    } else if (filter === "2") {
      dues = await duesDB.getOverdueByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
        year,
        month,
      });
    } else if (filter === "3") {
      dues = await duesDB.getByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
        year,
        month,
      });
    } else if (filter === "4") {
      dues = await duesDB.getDueByTypeByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        type: CONSTANTS.DUES_TYPES.RENT,
        dueDate: date,
      });
    } else {
      dues = await duesDB.getAllByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
      });
    }

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
        const tenant = await tenantDB.getById({
          id: due.tenantId,
        });
        due.kycStatus = tenant?.kycStatus || 0;

        const tenantDoc = await documentDB.getByTenantIdAndType({
          tenantId: tenant.id,
          type: CONSTANTS.DOCUMENT_TYPES.SELFI,
          moveOut: 0,
        });
        due.profilePicture = tenantDoc?.value || null;
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
    overDuesAmt = overDues;
    totalDuesForCurrentMonthAmt = duesForMonth;
    totalRentDuesAmt = rentDuesByType;
  }

  return {
    totalDuesAmt,
    totalDueTenantCount,
    duesList,
    overDuesAmt,
    totalDuesForCurrentMonthAmt,
    totalRentDuesAmt,
  };
};

export const duesForStaff = async (
  clientId: number,
  staffId: number,
  propId: number,
  tenantId: number,
  pageNum: number,
  limit: number,
  date: string,
  filter: string
) => {
  let totalDuesAmt = 0;
  let totalDueTenantCount = 0;
  let overDuesAmt = 0;
  let totalDuesForCurrentMonthAmt = 0;
  let totalRentDuesAmt = 0;
  let month = moment().format("M");
  let year = moment().format("YYYY");
  let duesList = [];

  if (propId) {
    //const { totalDues } = await duesDB.getTotalDuesByPropId({ propId, dueDate: date });
    const { totalDues } = await duesDB.getTotalDuesByPropId({ propId });
    const { overDues } = await duesDB.getTotalOverduesDuesByPropId({
      propId,
      year,
      month,
    });
    const { duesForMonth } = await duesDB.getTotalDuesByPropIdYearMonth({
      propId,
      year,
      month,
    });
    const { rentDuesByType } = await duesDB.getTotalDuesByTypeByPropId({
      propId,
      type: CONSTANTS.DUES_TYPES.RENT,
      year,
      month,
    });
    const { dueTenantCount } = await duesDB.getTenantCountByPropId({
      propId,
    });
    let dues = [];
    if (filter === "1") {
      dues = await duesDB.getAllByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
      });
    } else if (filter === "2") {
      //Overdues
      dues = await duesDB.getOverdueByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        year,
        month,
      });
    } else if (filter === "3") {
      //Jan Dues
      dues = await duesDB.getByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
      });
    } else {
      // Jan Rent Dues
      dues = await duesDB.getDueByTypeByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        type: CONSTANTS.DUES_TYPES.RENT,
        dueDate: date,
      });
    }

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
    overDuesAmt = overDues;
    totalDuesForCurrentMonthAmt = duesForMonth;
    totalRentDuesAmt = rentDuesByType;
  } else if (tenantId) {
    const { totalDues } = await duesDB.getTotalDuesByTenantId({
      tenantId,
      propId,
    });
    const { dueTenantCount } = await duesDB.getTenantCountByTenantId({
      tenantId,
    });
    const dues = await duesDB.getByTenantIdandPage({
      tenantId,
      pageNum: Number(pageNum),
      limit,
    });

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
  } else {
    const staffLinkedProps = await propertyDB.getPropsByStaffId({
      staffId,
    });
    if (staffLinkedProps) {
      const propertiesIds = staffLinkedProps
        .map((prop: propertiesTypes) => prop.id)
        .join(",");

      const { totalDues } = await duesDB.getTotalDuesForStaff({
        clientId,
        propertiesIds,
      });
      const { totalDues: duesForMonth } = await duesDB.getDuesByMonthForStaff({
        clientId,
        propertiesIds,
        year,
        month,
      });
      const { totalDues: overDues } = await duesDB.getTotalOverduesDuesForStaff({
          clientId,
          propertiesIds,
          month,
        });
      const { totalDues: rentDuesByType } = await duesDB.getTotalDuesByTypeForStaff({
          clientId,
          propertiesIds,
          type: CONSTANTS.DUES_TYPES.RENT,
          year,
          month,
        });

      const { dueTenantCount } = await duesDB.getTenantCountForStaff({
        clientId,
        propertiesIds,
      });
      let dues = [];
      if (filter === "1") {
        dues = await duesDB.getAllForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
        });
      } else if (filter === "2") {
        dues = await duesDB.getOverduesForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          dueDate: date,
        });
      } else if (filter === "3") {
        dues = await duesDB.getForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          dueDate: date,
        });
      } else {
        dues = await duesDB.getDueByTypeForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          type: CONSTANTS.DUES_TYPES.RENT,
          dueDate: date,
        });
      }

      if (dues) {
        for (let due of dues) {
          if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
            const { name } = await flatDB.getById({ id: due.flatId });
            due.flatName = name;
          } else {
            due.flatName = due.floor;
          }
        }
      }

      totalDuesAmt = totalDues;
      totalDueTenantCount = dueTenantCount;
      duesList = dues;
      overDuesAmt = overDues;
      totalDuesForCurrentMonthAmt = duesForMonth;
      totalRentDuesAmt = rentDuesByType;
    }
  }

  return {
    totalDuesAmt,
    totalDueTenantCount,
    duesList,
    overDuesAmt,
    totalDuesForCurrentMonthAmt,
    totalRentDuesAmt,
  };
};

export const duesForWeb = async (
  clientId: number,
  propId: number,
  tenantId: number,
  staffId: number,
  startDate: string,
  endDate: string,
  pageNum: number,
  limit: number,
  date: string,
  filter: string,
  s: string,
  t: number,
  locationId: number,
) => {
  let totalDuesAmt = 0;
  let totalDueTenantCount = 0;
  let overDuesAmt = 0;
  let totalDuesForCurrentMonthAmt = 0;
  let totalRentDuesAmt = 0;
  let securityShortFall = 0;
  let utilityDuesAmt = 0;
  let otherDuesAmt = 0;
  let fineDuesAmt = 0;
  let month = moment().format("M");
  let year = moment().format("YYYY");
  let duesList = [];
  let dues = [];

  if (s && s !== "undefined" && s !== "null" && s !== " ") {
    if (propId && Number(propId) !== 0) {
      const { totalDues } = await duesDB.getTotalDuesByPropId({ propId });
      const { overDues } = await duesDB.getTotalOverduesDuesByPropId({
        propId,
        year,
        month,
      });
      const { duesForMonth } = await duesDB.getTotalDuesByPropIdYearMonth({
        propId,
        year,
        month,
      });
      const { rentDuesByType } = await duesDB.getTotalDuesByTypeByPropId({
        propId,
        type: CONSTANTS.DUES_TYPES.RENT,
        year,
        month,
      });
  
      const { dueTenantCount } = await duesDB.getTenantCountByPropId({
        propId,
      });

      const { utilityDues } = await duesDB.getTotalUtilityDuesByPropId({
        propId,
        startDate,
        endDate,
      });

      const { otherDues } = await duesDB.getTotalOtherDuesByPropId({
        propId,
        startDate,
        endDate,
      });

      const { fineDues } = await duesDB.getTotalFineDuesByPropId({
        propId,
        startDate,
        endDate,
      });

      const securityShortFallAmt = await duesDB.getSecurityShortFallAmtForProp({
        clientId,
        propId,
      });
  
      dues = await duesDB.getByPropIdAndSearch({
        propId,
        searchVal: s,
        searchType: t,
      });

      totalDuesAmt = totalDues;
      totalDueTenantCount = dueTenantCount;
      duesList = dues;
      overDuesAmt = overDues;
      totalDuesForCurrentMonthAmt = duesForMonth;
      totalRentDuesAmt = rentDuesByType;
      securityShortFall = securityShortFallAmt.totalDifference;
      utilityDuesAmt = utilityDues || 0;
      otherDuesAmt = otherDues || 0;
      fineDuesAmt = fineDues || 0;
    } else {
      const { totalDues } = await duesDB.getTotalDuesByClientId({
        clientId,
        dueDate: date,
      });
      const { overDues } = await duesDB.getTotalOverduesByClientId({
        clientId,
        year,
        month,
      });
      const { duesForMonth } = await duesDB.getDuesByMonth({
        clientId,
        year,
        month,
      });
      const { rentDuesByType } = await duesDB.getTotalDuesByType({
        clientId,
        type: CONSTANTS.DUES_TYPES.RENT,
        year,
        month,
      });
      const {utilityDues} = await duesDB.getTotalUtilityDuesForMonth({
        clientId,
        startDate,
        endDate,
      });
      const {otherDues} = await duesDB.getTotalOtherDuesForMonth({
        clientId,
        startDate,
        endDate,
      });
      const {fineDues} = await duesDB.getTotalFineDuesForMonth({
        clientId,
        startDate,
        endDate,
      });
      const { dueTenantCount } = await duesDB.getTenantCount({ clientId, date });

      const securityShortFallAmt = await duesDB.getSecurityShortFallAmtForClient({
        clientId,
      });
  
      dues = await duesDB.getByTenantNameMobileForClient({
        clientId,
        searchVal: s,
        searchType: t,
      });
      totalDuesAmt = totalDues;
      totalDueTenantCount = dueTenantCount;
      duesList = dues;
      overDuesAmt = overDues;
      totalDuesForCurrentMonthAmt = duesForMonth;
      totalRentDuesAmt = rentDuesByType;
      securityShortFall = securityShortFallAmt.totalDifference;
      utilityDuesAmt = utilityDues || 0;
      otherDuesAmt = otherDues || 0;
      fineDuesAmt = fineDues || 0;
    }
  } else if (propId) {
    const { totalDues } = await duesDB.getTotalDuesByPropId({ propId });
    const { overDues } = await duesDB.getTotalOverduesDuesByPropId({
      propId,
      year,
      month,
    });
    const { duesForMonth } = await duesDB.getTotalDuesByPropIdYearMonth({
      propId,
      year,
      month,
    });
    const { rentDuesByType } = await duesDB.getTotalDuesByTypeByPropIdAndDateRange({
      propId,
      type: CONSTANTS.DUES_TYPES.RENT,
      startDate,
      endDate,
    });

    const { utilityDues } = await duesDB.getTotalUtilityDuesByPropId({
      propId,
      startDate,
      endDate,
    });

    const { otherDues } = await duesDB.getTotalOtherDuesByPropId({
      propId,
      startDate,
      endDate,
    });

    const { fineDues } = await duesDB.getTotalFineDuesByPropId({
      propId,
      startDate,
      endDate,
    });

    // const { todayTotalDues } = await duesDB.getTotalDuesByPropIdDateRange({
    //   propId,
    //   startDate,
    //   endDate,
    // });
    // const { todayRentDuesByType } =
    //   await duesDB.getTotalDuesByTypeByPropIdDateRange({
    //     propId,
    //     type: CONSTANTS.DUES_TYPES.RENT,
    //     startDate,
    //     endDate,
    //   });

    const { dueTenantCount } = await duesDB.getTenantCountByPropId({
      propId,
    });

    const securityShortFallAmt = await duesDB.getSecurityShortFallAmtForProp({
      clientId,
      propId,
    });


    if (filter === "CRD") {
      //Cur Rent Month Dues
      dues = await duesDB.getDueByTypeByPropIdandPageAndDateRange({
        propId,
        pageNum: Number(pageNum),
        limit,
        type: CONSTANTS.DUES_TYPES.RENT,
        startDate,
        endDate,
      });
    } else if (filter === "CUD") {
      //Current Month Utility Dues
      dues = await duesDB.getUtilityDueByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate,
      });
    } else if (filter === "COD") {
      //Current Month Other Dues
      dues = await duesDB.getOtherDueByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate,
      });
    } else if (filter === "FD") {
      //Fine Dues
      dues = await duesDB.getFineDueByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate,
      });
    } else if (filter === "OD") {
      //Overdues
      dues = await duesDB.getOverdueByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        year,
        month,
      });
    } else if (filter === "CMD") {
      //Cur Month Dues
      dues = await duesDB.getByPropIdandPage({
        propId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
      });
    } else if (filter === "TD") {
      dues = await duesDB.getByPropId({
        propId,
      });
    } else if (filter === "SSD") {
      //Security Shortfall Dues
      dues = await duesDB.getSecurityShortFallDuesForProp({
        clientId,
        propId,
      });
    } else if (filter === "MA" || filter === "MI" || filter === "DDMA" || filter === "DDMI") {
      dues = await duesDB.getByClientIdAndPropIdandDateRangeAndSortBy({
        clientId,
        propId,
        startDate,
        endDate,
        sortBy: filter,
      });
    } else if (filter === "HD") {
      //Hidden Dues
      dues = await hiddenDuesDB.getByPropId({ clientId, propId });
    } else if (filter === "5OD") {
      dues = await duesDB.getByClientIdAndPropIdAndOverDueDuration({
        clientId,
        propId,
        overDueDuration: 5,
      });
    } else if (filter === "10OD") {
      dues = await duesDB.getByClientIdAndPropIdAndOverDueDuration({
        clientId,
        propId,
        overDueDuration: 10,
      });
    } else if (filter === "20OD") {
      dues = await duesDB.getByClientIdAndPropIdAndOverDueDuration({
        clientId,
        propId,
        overDueDuration: 20,
      });
    } else if (filter === "30OD") {
      dues = await duesDB.getByClientIdAndPropIdAndOverDueDuration({
        clientId,
        propId,
        overDueDuration: 30,
      });
    } else {
      // Total Dues
      if (startDate && endDate) {
        dues = await duesDB.getByPropIdandDateRange({
          propId,
          startDate,
          endDate,
        });
      } else {
        dues = await duesDB.getByPropId({
          propId,
        });
      }
    }

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
    overDuesAmt = overDues;
    totalDuesForCurrentMonthAmt = duesForMonth;
    totalRentDuesAmt = rentDuesByType;
    securityShortFall = securityShortFallAmt.totalDifference;
    utilityDuesAmt = utilityDues || 0;
    otherDuesAmt = otherDues || 0;
    fineDuesAmt = fineDues || 0;
  } else if (locationId) {
    const { totalDues } = await duesDB.getTotalDuesByLocation({ locationId });
    const { overDues } = await duesDB.getTotalOverduesDuesByLocation({
      locationId,
      year,
      month,
    });
    const { duesForMonth } = await duesDB.getTotalDuesByLocationYearMonth({
      locationId,
      year,
      month,
    });
    const { rentDuesByType } = await duesDB.getTotalDuesByTypeByLocationAndDateRange({
      locationId,
      type: CONSTANTS.DUES_TYPES.RENT,
      startDate,
      endDate,
    });

    const { utilityDues } = await duesDB.getTotalUtilityDuesByLocation({
      locationId,
      startDate,
      endDate,
    });

    const { otherDues } = await duesDB.getTotalOtherDuesByLocation({
      locationId,
      startDate,
      endDate,
    });

    const { fineDues } = await duesDB.getTotalFineDuesByLocation({
      locationId,
      startDate,
      endDate,
    });

    const { dueTenantCount } = await duesDB.getTenantCountByLocation({
      locationId,
    });

    const securityShortFallAmt = await duesDB.getSecurityShortFallAmtForLocation({
      clientId,
      locationId,
    });

    if (filter === "CRD") {
      //Cur Rent Month Dues
      dues = await duesDB.getDueByTypeByLocationIdandPageAndDateRange({
        locationId: locationId,
        pageNum: Number(pageNum),
        limit,
        type: CONSTANTS.DUES_TYPES.RENT,
        startDate,
        endDate,
      });
    } else if (filter === "CUD") {
      //Current Month Utility Dues
      dues = await duesDB.getUtilityDueByLocationIdandPage({
        locationId: locationId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate,
      });
    } else if (filter === "COD") {
      //Current Month Other Dues
      dues = await duesDB.getOtherDueByLocationIdandPage({
        locationId: locationId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate,
      });
    } else if (filter === "FD") {
      //Fine Dues
      dues = await duesDB.getFineDueByLocationIdandPage({
        locationId: locationId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate,
      });
    } else if (filter === "TD") {
      dues = await duesDB.getByPropId({
        propId,
      });
    } else if (filter === "SSD") {
      //Security Shortfall Dues
      dues = await duesDB.getSecurityShortFallDuesForLocation({
        clientId,
        locationId,
      });
    } else if (filter === "MA" || filter === "MI" || filter === "DDMA" || filter === "DDMI") {
      dues = await duesDB.getByClientIdAndLocationIdandDateRangeAndSortBy({
        clientId,
        locationId,
        startDate,
        endDate,
        sortBy: filter,
      });
    } else if (filter === "HD") {
      //Hidden Dues
      dues = await hiddenDuesDB.getByLocationId({ clientId, locationId });
    } else if (filter === "5OD") {
      dues = await duesDB.getByClientIdAndLocationIdAndOverDueDuration({
        clientId,
        locationId,
        overDueDuration: 5,
      });
    } else if (filter === "10OD") {
      dues = await duesDB.getByClientIdAndLocationIdAndOverDueDuration({
        clientId,
        locationId,
        overDueDuration: 10,
      });
    } else if (filter === "20OD") {
      dues = await duesDB.getByClientIdAndLocationIdAndOverDueDuration({
        clientId,
        locationId,
        overDueDuration: 20,
      });
    } else if (filter === "30OD") {
      dues = await duesDB.getByClientIdAndLocationIdAndOverDueDuration({
        clientId,
        locationId,
        overDueDuration: 30,
      });
    } else {
      dues = await duesDB.getByClientIdAndLocation({
        clientId,
        locationId,
        startDate,
        endDate,
      });
    }

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
    overDuesAmt = overDues;
    totalDuesForCurrentMonthAmt = duesForMonth;
    totalRentDuesAmt = rentDuesByType;
    securityShortFall = securityShortFallAmt.totalDifference;
    utilityDuesAmt = utilityDues || 0;
    otherDuesAmt = otherDues || 0;
    fineDuesAmt = fineDues || 0;
  } else if (tenantId) {
    const { totalDues } = await duesDB.getTotalDuesByTenantId({
      tenantId,
      propId,
      date,
    });
    const { dueTenantCount } = await duesDB.getTenantCountByTenantId({
      tenantId,
      date,
    });
    const dues = await duesDB.getByTenantIdandPage({
      tenantId,
      pageNum: Number(pageNum),
      limit,
      date,
    });

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
  } else if (staffId && Number(staffId) !== 0) {
    const staffLinkedProps = await propertyDB.getPropsByStaffId({
      staffId,
    });
    if (staffLinkedProps) {
      const propertiesIds = staffLinkedProps
        .map((prop: propertiesTypes) => prop.id)
        .join(",");

      const { totalDues } = await duesDB.getTotalDuesForStaff({
        clientId,
        propertiesIds,
      });
      const { totalDues: duesForMonth } = await duesDB.getDuesByMonthForStaff({
        clientId,
        propertiesIds,
        year,
        month,
      });
      const { overDues } = await duesDB.getTotalOverduesByClientIdForStaff({
          clientId,
          propertiesIds,
          year,
          month,
        });
      const { totalDues: rentDuesByType } = await duesDB.getTotalDuesByTypeAndDateRangeForStaff({
          clientId,
          propertiesIds,
          type: CONSTANTS.DUES_TYPES.RENT,
          startDate,
          endDate,
        });
      const { utilityDues } = await duesDB.getTotalUtilityDuesForStaff({
          clientId,
          propertiesIds,
          startDate,
          endDate,
        });
      const { otherDues } = await duesDB.getTotalOtherDuesForStaff({
          clientId,
          propertiesIds,
          startDate,
          endDate,
        });
      const { fineDues } = await duesDB.getTotalFineDuesForStaff({
          clientId,
          propertiesIds,
          startDate,
          endDate,
        });
      const { dueTenantCount } = await duesDB.getTenantCountForStaff({
        clientId,
        propertiesIds,
      });
      const securityShortFallAmt = await duesDB.getSecurityShortFallAmtForStaff({
        clientId,
        propertiesIds
      });

      let dues = [];

      if (filter === "TD") {
        dues = await duesDB.getByClientIdForStaff({
          clientId,
          propertiesIds,
        });
      } else if (filter === "OD") {
        dues = await duesDB.getOverduesForStaffByPage ({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          year,
          month,
        });
      } else if (filter === "CMD") {
        dues = await duesDB.getForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          dueDate: date,
        });
      } else if (filter === "CRD") {
        dues = await duesDB.getDueByTypeAndDateRangeForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          type: CONSTANTS.DUES_TYPES.RENT,
          startDate,
          endDate,
        });
      } else if (filter === "CUD") {
        //Current Month Utility Dues
        dues = await duesDB.getUtilityDueForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          startDate,
          endDate,
        });
      } else if (filter === "COD") {
        //Current Month Other Dues
        dues = await duesDB.getOtherDueForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          startDate,
          endDate,
        });
      } else if (filter === "FD") {
        //Fine Dues
        dues = await duesDB.getFineDueForStaffByPage({
          propertiesIds,
          pageNum: Number(pageNum),
          limit,
          startDate,
          endDate,
        });
      } else if (filter === "SSD") {
        //Security Shortfall Dues
        dues = await duesDB.getSecurityShortFallDuesForStaff({
          clientId,
          propertiesIds,
        });
      }else if (filter === "MA" || filter === "MI" || filter === "DDMA" || filter === "DDMI") {
        dues = await duesDB.getByClientIdandDateRangeAndSortByForStaff({
          clientId,
          propertiesIds,
          startDate,
          endDate,
          sortBy: filter,
        });
      } else if (filter === "HD") {
        //Hidden Dues
        dues = await hiddenDuesDB.getByClientIdForStaff({ clientId, propertiesIds });
      } else if (filter === "5OD") {
        dues = await duesDB.getByClientIdAndOverDueDurationForStaff({
          clientId,
          propertiesIds,
          overDueDuration: 5,
        });
      } else if (filter === "10OD") {
        dues = await duesDB.getByClientIdAndOverDueDurationForStaff({
          clientId,
          propertiesIds,
          overDueDuration: 10,
        });
      } else if (filter === "20OD") {
        dues = await duesDB.getByClientIdAndOverDueDurationForStaff({
          clientId,
          propertiesIds,
          overDueDuration: 20,
        });
      } else if (filter === "30OD") {
        dues = await duesDB.getByClientIdAndOverDueDurationForStaff({
          clientId,
          propertiesIds,
          overDueDuration: 30,
        });
      } else {
        if (startDate && endDate) {
          dues = await duesDB.getByClientIdandDateRangeForStaff({
            clientId,
            propertiesIds,
            startDate,
            endDate,
          });
        } else {
          dues = await duesDB.getDueByTypeForStaffByPage({
            propertiesIds,
            pageNum: Number(pageNum),
            limit,
            type: CONSTANTS.DUES_TYPES.RENT,
            dueDate: date,
          });
        } 
      }

      if (dues) {
        for (let due of dues) {
          if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
            const { name } = await flatDB.getById({ id: due.flatId });
            due.flatName = name;
          } else {
            due.flatName = due.floor;
          }
        }
      }

      totalDuesAmt = totalDues;
      totalDueTenantCount = dueTenantCount;
      duesList = dues;
      overDuesAmt = overDues;
      totalDuesForCurrentMonthAmt = duesForMonth;
      totalRentDuesAmt = rentDuesByType;
      securityShortFall = securityShortFallAmt.totalDifference;
      utilityDuesAmt = utilityDues || 0;
      otherDuesAmt = otherDues || 0;
      fineDuesAmt = fineDues || 0;
    }
  } else {
    const { totalDues } = await duesDB.getTotalDuesByClientId({
      clientId,
      dueDate: date,
    });
    const { overDues } = await duesDB.getTotalOverduesByClientId({
      clientId,
      year,
      month,
    });
    const { duesForMonth } = await duesDB.getDuesByMonth({
      clientId,
      year,
      month,
    });
    const { rentDuesByType } = await duesDB.getTotalDuesByTypeAndDateRange({
      clientId,
      type: CONSTANTS.DUES_TYPES.RENT,
      startDate,
      endDate,
    });
    const {utilityDues} = await duesDB.getTotalUtilityDuesForMonth({
      clientId,
      startDate,
      endDate,
    });
    const {otherDues} = await duesDB.getTotalOtherDuesForMonth({
      clientId,
      startDate,
      endDate,
    });
    const {fineDues} = await duesDB.getTotalFineDuesForMonth({
      clientId,
      startDate,
      endDate,
    });
    const { dueTenantCount } = await duesDB.getTenantCount({ clientId, date });

    const securityShortFallAmt = await duesDB.getSecurityShortFallAmtForClient({
      clientId,
    });

    let dues = [];
    if (filter === "TD") {
      //totalDues
      dues = await duesDB.getByClientId({
        clientId,
      });
    } else if (filter === "OD") {
      //OverDues
      dues = await duesDB.getOverdueByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
        year,
        month,
      });
    } else if (filter === "CMD") {
      //Current Month Dues
      dues = await duesDB.getByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        dueDate: date,
        year,
        month,
      });
    } else if (filter === "CRD") {
      //Current Month Rent Dues
      dues = await duesDB.getDueByTypeByClientIdandPageAndDateRange({
        clientId,
        pageNum: Number(pageNum),
        limit,
        type: CONSTANTS.DUES_TYPES.RENT,
        startDate,
        endDate,
      });
    } else if (filter === "CUD") {
      //Current Month Utility Dues
      dues = await duesDB.getUtilityDueByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate
      });
    } else if (filter === "COD") {
      //Current Month Other Dues
      dues = await duesDB.getOtherDueByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate,
      });
    } else if (filter === "FD") {
      //Fine Dues
      dues = await duesDB.getFineDueByClientIdandPage({
        clientId,
        pageNum: Number(pageNum),
        limit,
        startDate,
        endDate,
      });
    } else if (filter === "SSD") {
      //Security Shortfall Dues
      dues = await duesDB.getSecurityShortFallDuesForClient({
        clientId,
      });
    } else if (filter === "MA" || filter === "MI" || filter === "DDMA" || filter === "DDMI") {
      //Sort By
      dues = await duesDB.getByClientIdandDateRangeAndSortBy({
        clientId,
        startDate,
        endDate,
        sortBy: filter,
      });
    } else if (filter === "HD") {
      //Hidden Dues
      dues = await hiddenDuesDB.getByClientId({ clientId });
    } else if (filter === "5OD") {
      dues = await duesDB.getByClientIdAndOverDueDuration({
        clientId,
        overDueDuration: 5,
      });
    } else if (filter === "10OD") {
      dues = await duesDB.getByClientIdAndOverDueDuration({
        clientId,
        overDueDuration: 10,
      });
    } else if (filter === "20OD") {
      dues = await duesDB.getByClientIdAndOverDueDuration({
        clientId,
        overDueDuration: 20,
      });
    } else if (filter === "30OD") {
      dues = await duesDB.getByClientIdAndOverDueDuration({
        clientId,
        overDueDuration: 30,
      });
    } else {
      if (startDate && endDate) {
        dues = await duesDB.getByClientIdandDateRange({
          clientId,
          startDate,
          endDate,
        });
      } else {
        dues = await duesDB.getAllByClientIdandPage({
          clientId,
          pageNum: Number(pageNum),
          limit,
          dueDate: date,
        });
      }
    }

    if (dues) {
      for (let due of dues) {
        if (due.propertyType === CONSTANTS.PROPERTY_TYPE.FLAT) {
          const { name } = await flatDB.getById({ id: due.flatId });
          due.flatName = name;
        } else {
          due.flatName = due.floor;
        }
      }
    }

    totalDuesAmt = totalDues;
    totalDueTenantCount = dueTenantCount;
    duesList = dues;
    overDuesAmt = overDues;
    totalDuesForCurrentMonthAmt = duesForMonth;
    totalRentDuesAmt = rentDuesByType;
    securityShortFall = securityShortFallAmt.totalDifference;
    utilityDuesAmt = utilityDues || 0;
    otherDuesAmt = otherDues || 0;
    fineDuesAmt = fineDues || 0;
  }

  return {
    totalDuesAmt,
    totalDueTenantCount,
    duesList,
    overDuesAmt,
    totalDuesForCurrentMonthAmt,
    totalRentDuesAmt,
    securityShortFall,
    utilityDuesAmt,
    otherDuesAmt,
    fineDuesAmt,
  };
};
