front/controllers/buynow/common.js

/* ============================================================================ *\
|| ########################################################################## ||
|| # Auction Software Marketplace          Release: 0.6   Build 0.7         # ||
|| # ---------------------------------------------------------------------- # ||
|| # License # 35YAHCNR9344X6O666C123AB                                     # ||
|| # ---------------------------------------------------------------------- # ||
|| # Copyright ©2014–2021 Develop Scripts LLC. All Rights Reserved          # ||
|| # This file may not be redistributed in whole or significant part.       # ||
|| # ------------- AUCTION SOFTWARE IS NOT FREE SOFTWARE ------------------ # ||
|| # http://www.auctionsoftwaremarketplace.com|support@auctionsoftware.com  # ||
|| # ---------------------------------------------------------------------- # ||
|| ########################################################################## ||
\* ============================================================================ */

/* eslint-disable prefer-destructuring */
/* eslint-disable no-param-reassign */
const _ = require('underscore')

const Avatax = require('../../modules/tax/avalara').default

const shippingArtaCtrl = require('../shipping/arta/common')
const shippingShipEngineCtrl = require('../shipping/shipengine/common')

const buynowModule = require('../../modules/buynow').default

const commonFunction = require('../../../common/function').default

const avatax = new Avatax()
/**
 * Get cart total
 *
 * @memberOf frontend.buynow
 * @param {object} cartValues cartValues
 * @param {object} items itmes
 * @param {string} type type can be buynow, cart, invoice
 */
const getCartTotal = async (cartValues, items, type) => {
    let perTotal = 0
    let totalDueAmount = 0
    let depositAmount = 0
    let processingAmount = 0
    let paidAmount = 0
    if (items.per_total) {
        perTotal = items.per_total
    } else if (items.amount) {
        perTotal = items.amount
    }
    cartValues.per_total += perTotal

    totalDueAmount = items.total_amount ? items.total_amount : 0
    if (items.admin_fee) {
        processingAmount = items.admin_fee
    }

    if (type === 'invoice') {
        if (items.buynow_autype !== 'buynow') {
            if (items.deposit_amount) {
                depositAmount = items.deposit_amount
            } else if (items.projects_deposit_amount) {
                depositAmount = items.projects_deposit_amount
            }
        }
    } else if (type !== 'buynow') {
        if (items.deposit_amount) {
            depositAmount = items.deposit_amount
        } else if (items.projects_deposit_amount) {
            depositAmount = items.projects_deposit_amount
        }
    }

    paidAmount = items.paid_amount ? items.paid_amount : 0

    if (totalDueAmount) {
        totalDueAmount -= depositAmount
        totalDueAmount += processingAmount
    }

    cartValues.total_due_amount += parseFloat(parseFloat(totalDueAmount).toFixed(2))
    cartValues.total_amount += items.total_amount ? items.total_amount : 0
    cartValues.total_tax += items.total_tax ? items.total_tax : 0
    cartValues.total_shipping += items.total_shipping ? items.total_shipping : 0
    cartValues.total_premium += items.total_premium ? items.total_premium : 0
    cartValues.total_deposit += depositAmount
    cartValues.admin_fee += items.admin_fee ? items.admin_fee : 0
    cartValues.admin_fee_percent += items.admin_fee_percent ? items.admin_fee_percent : 0

    if (!cartValues.total_paid) {
        cartValues.total_paid = paidAmount
        cartValues.total_due_amount -= cartValues.total_paid
    }

    if (type === 'cart') {
        cartValues.cart_id = [...(cartValues.cart_id || []), items.id]
    } else if (type === 'buynow' || type === 'invoice') {
        cartValues.cart_id = [...(cartValues.cart_id || []), items.cart_id]
    }

    return cartValues
}
/**
 * check calculation function
 *
 * @memberOf frontend.checkcalculationFun
 * @param {string} value values
 * @param {number} itemsPrice itmes price
 * @param {object} items object of times
 */
const checkcalculationFun = async (value, itemsPrice, items) => {
    const configCal = global.calculations[value]
    const type = configCal.value
    const totalValues = {
        percent: 0,
        total: 0,
        percentVal: 0,
    }
    if (configCal.value_from === 'table') {
        totalValues.percentVal = parseFloat(items[configCal.value_variable]).toFixed(2)
    } else if (configCal.value_from === 'config') {
        if (typeof global.configurations.variables[type] !== 'undefined') {
            if (global.configurations.variables[type]) {
                totalValues.percentVal = parseFloat(global.configurations.variables[type]).toFixed(
                    2,
                )
            }
        }
    } else if (configCal.value_from === 'third_party') {
        totalValues.percentVal = 0
        if (configCal.value_variable === 'avalara') {
            totalValues.percentVal = await avatax.calculateTax({ item: items })
        }
        if (configCal.value_variable === 'table') {
            if (configCal.value === 'shipping') {
                const shippingType = items[type] || items.projects_shipping
                if (shippingType === 'arta') {
                    totalValues.percentVal = await shippingArtaCtrl.calculateShipping({
                        item: items,
                    })
                } else if (shippingType === 'shipEngine') {
                    totalValues.percentVal = await shippingShipEngineCtrl.calculateShipping({
                        item: items,
                    })
                }
            }
        }
    }

    if (configCal.value_type === 'percentage') {
        totalValues.percent = parseFloat(totalValues.percentVal).toFixed(2)
        totalValues.total = (itemsPrice * (totalValues.percent / 100)).toFixed(2)
    } else if (configCal.value_type === 'amount') {
        totalValues.percent = parseFloat((totalValues.percentVal * 100) / itemsPrice).toFixed(2)
        totalValues.total = parseFloat(totalValues.percentVal).toFixed(2)
    }
    return totalValues
}
/**
 * cart items caluctions
 *
 * @memberOf frontend.cartItemsCalculations
 * @param {object} items object of times
 */
const cartItemsCalculations = async (items) => {
    const cartValues = {
        per_total: 0,
        total_amount: 0,
        tax_percent: 0,
        total_tax: 0,
        shipping_percent: 0,
        total_shipping: 0,
        buyer_premium_percent: 0,
        total_premium: 0,
        cart_group: items.group_carts || '1',
        delivery_type: 0,
    }
    if (items.product_type === 'buynow') {
        cartValues.per_total = commonFunction.multipleFloat(
            parseFloat(items.bprice).toFixed(2),
            parseFloat(items.qty_add).toFixed(2),
        )
    } else if (items.product_type === 'live') {
        cartValues.per_total = parseFloat(items.wprice || items.per_total).toFixed(2)
    } else if (items.product_type === 'multible_auction') {
        cartValues.per_total = commonFunction.multipleFloat(
            parseFloat(items.wprice || items.per_total).toFixed(2),
            parseFloat(items.qty_add).toFixed(2),
        )
    }

    if (items.local_pickup_check === 1) {
        cartValues.delivery_type = 'local_pickup'
    } else if (items.shipping_check === 1) {
        cartValues.delivery_type = 'shipping'
    } else {
        cartValues.delivery_type = 'local_pickup'
    }

    if (typeof global.calculations.tax !== 'undefined') {
        if (global.calculations.tax.enabled) {
            const cartCalculation = await checkcalculationFun('tax', cartValues.per_total, items)
            cartValues.total_tax = cartCalculation.total
            cartValues.tax_percent = cartCalculation.percent
        }
    }

    if (typeof global.calculations.buyer_premium !== 'undefined') {
        if (global.calculations.buyer_premium.enabled) {
            const cartCalculation = await checkcalculationFun(
                'buyer_premium',
                cartValues.per_total,
                items,
            )
            cartValues.total_premium = cartCalculation.total
            cartValues.buyer_premium_percent = cartCalculation.percent
        }
    }
    if (typeof global.calculations.shipping !== 'undefined') {
        if (global.calculations.shipping.enabled) {
            const cartCalculation = await checkcalculationFun(
                'shipping',
                cartValues.per_total,
                items,
            )
            cartValues.total_shipping = cartCalculation.total
            cartValues.shipping_percent = cartCalculation.percent
        }
    }

    // if (
    //     typeof global.configFeatures.premium_deduction !== 'undefined' &&
    //     global.configFeatures.premium_deduction.enabled
    // ) {
    //     cartValues.per_total -= cartValues.total_premium
    // }

    const cartTotal = commonFunction.sumFloat(
        parseFloat(cartValues.per_total).toFixed(2),
        parseFloat(cartValues.total_premium).toFixed(2),
    )
    const cartTotalTax = commonFunction.sumFloat(
        parseFloat(cartValues.total_tax).toFixed(2),
        parseFloat(cartValues.total_shipping).toFixed(2),
    )
    cartValues.total_amount = commonFunction.sumFloat(
        parseFloat(cartTotal).toFixed(2),
        parseFloat(cartTotalTax).toFixed(2),
    )
    if (
        (typeof global.configFeatures.premium_not_include !== 'undefined' &&
            global.configFeatures.premium_not_include.enabled) ||
        global.configFeatures.premium_not_include
    ) {
        cartValues.total_amount -= cartValues.total_premium
    }
    cartValues.total_amount = parseFloat(cartValues.total_amount).toFixed(2)
    console.log('total', cartValues)
    return cartValues
}
/**
 * cart items caluctions
 *
 * @memberOf frontend.cartItemsCalculations
 * @param {}
 * @param {object} cartValues object of times
 * @param {object} cartID cart id
 * @param {object} userID user id
 *
 */
const updateBuyNowCalculations = async (cartValues, cartID, userID) => {
    const [cartData] = await Promise.all([
        buynowModule.updateBuyNowData(cartValues, cartID, userID),
    ])
    return cartData
}
/**
 * cart items caluctions
 *
 * @memberOf frontend.cartItemsCalculations
 * @param {object} cartValues object of times
 * @param {object} cartID cart id
 * @param {object} userID user id
 *
 */
const getSingleCartDetails = async (req, groupID, cartID) => {
    let cartItems = []
    delete req.body.group_id
    delete req.body.cart_id
    if (groupID) {
        req.body.group_id = groupID
        ;[cartItems] = await Promise.all([buynowModule.allCartItems(req, req.body, 1)])
    } else {
        req.body.cart_id = cartID
        ;[cartItems] = await Promise.all([buynowModule.allCartItems(req, req.body, 1)])
    }

    const cartValues = {
        per_total: 0,
        total_amount: 0,
        total_tax: 0,
        total_shipping: 0,
        total_premium: 0,
        total_paid: 0,
        total_deposit: 0,
        total_due_amount: 0,
        cart_group: groupID,
        cart_id: [],
        common_invoice: 0,
        user_id: cartItems.length ? cartItems[0].user_id : 0,
    }

    await commonFunction.asyncForEach(cartItems, async (items) => {
        await getCartTotal(cartValues, items, 'buynow')
    })

    const responseData = { cartItems, cartValues }
    return responseData
}
/**
 * calculate Array Increment
 *
 * @memberOf frontend.cartItemsCalculations
 * @param {object} allIncrement object of times
 * @param {object} defaultIncrement cart id
 * @param {number} amount user id
 * @param {number} isPercentage
 *
 */
const calculateArrayIncrement = (allIncrement, defaultIncrement, amount, isPercentage = 0) => {
    const amounttoCheck = parseInt(amount, 10)
    let tosendAmount = 0
    if (allIncrement.length > 0) {
        allIncrement.forEach((element) => {
            if (
                parseInt(element.from_amount, 10) <= amounttoCheck &&
                parseInt(element.to_amount, 10) >= amounttoCheck
            ) {
                if (isPercentage) {
                    tosendAmount =
                        element.value_type === 'percentage'
                            ? parseFloat(element.increment)
                            : (parseFloat(element.increment) / amounttoCheck) * 100
                } else {
                    tosendAmount = parseInt(element.increment, 10)
                }
            }
        })

        if (tosendAmount === 0) {
            if (defaultIncrement.length > 0) {
                tosendAmount = defaultIncrement[0].increment
            }
        }
    } else if (defaultIncrement.length > 0) {
        tosendAmount = defaultIncrement[0].increment
    }
    return tosendAmount
}

module.exports = {
    getCartTotal,
    cartItemsCalculations,
    checkcalculationFun,
    updateBuyNowCalculations,
    getSingleCartDetails,
    calculateArrayIncrement,
}