const request = require('request-promise');
const AutoGenerator = require("../../models/AutoGenerator");
const ShopperrSubscribeProducts = require("../../models/ShopperrSubscribeProducts");
const User = require("../../models/User");
const { updateShopperrPriceAlgo } = require("../../controllers/middlewares/priceAlgo");
var mongoose = require("mongoose"); 
const Lead = require("../../models/Lead");
const SubscribeProducts = require('../../models/SubscribeProducts');
const Products = require('../../models/Products');
const CsvUpload = require('../../models/CsvUpload');
const AWS = require('aws-sdk')
const ID = '';
const SECRET = '';
const s3 = new AWS.S3({
    accessKeyId: ID,
    secretAccessKey: SECRET
});
// The name of the bucket that you have created
const BUCKET_NAME = 'test-bucket';
async function addMerchantSubscribedProductCron(type = 4, module){ 
    if(!module){
        return false;
    }
    var limit = 1;  
    var csvRequest = await CsvUpload.find({ $and: [{"status": 0} , {"type" : type}]}).limit(parseInt(limit)).sort({'_id' :-1 }); 
    if(csvRequest.length > 0){ 
        var obj = {  
            status: 1 
        }  
        try { 
            const data = await CsvUpload.updateOne({"_id" : csvRequest['0']._id },{ $set: obj } , {upsert: false}); 
        } catch (err) { 
            
        } 
        var options = {
            uri: csvRequest[0].url,
            encoding: null
        };
        var merchantId = csvRequest[0].mId;
        request(options, async function(error, response, body) {
            if (error || response.statusCode !== 200) { 
                
                
            } else { 
                let csvData = await csv().fromString(body.toString());
                csvData = JSON.stringify(csvData);
                csvData = JSON.parse(csvData); 
                let upStatus = await merchantSubscribeList(module,csvData , merchantId);
                
            }
        });
    }else{
        
    }
};
  
async function merchantSubscribeList(module,items,merchantId){
    if(!items || (items && !items.length))
      return false;
    let skus = items.map((item)=>{
      return item.Sku;
    });
    const products = await Products.find({'code' :{ $in: skus }}).exec();
    const productIds = products.map((produt)=>{
      return produt._id;
    });
    const alreadySubscribed = await module.find({$and:[{pId:{$in:productIds}},{mId:merchantId}]});
    const alreadySubscribedId = alreadySubscribed.map((item)=>{ 
      return item.pId;
    });
    const subscribeProducts = [];
    products.forEach((product)=>{
      const item = items.find((ele)=>ele.Sku == product.code);
      if(alreadySubscribedId.includes(product._id) !== -1 && item){
        subscribeProducts.push({ 
          mId     : merchantId, 
          pId     : product._id,
          margin  : item.Margin,
          dos     :  new Date(),
          dom     :  new Date(),
          am_status : 0,
          [mongooseConstantValues.IS_AMAZON_PRODUCT_UPLOADED]:item[mongooseConstantValues.IS_AMAZON_PRODUCT_UPLOADED]
        });
      }
    });
    const update = await module.insertMany(subscribeProducts);
    return update;
}

  async function upload_image(handle, callback) {
    var d = new Date();//
    const imageDir = "images/" + d.getFullYear().toString() + "/" + (d.getMonth() + 1).toString() + "/" + handle.handle  + "/";
    var s3dir = `${imageDir}`;
    var filename = Date.now().toString()+ makeid(6) +'.png';
    var options = {
        uri: handle.url,
        encoding: null
    };
    request(options, async function(error, response, body) {
        if (error || response.statusCode !== 200) { 
            
            
        } else { 
             var status = await uploadFile(body, s3dir + filename);             
        }   
    });
    callback(s3dir + filename);
  }
  
  async function uploadFile(file, key) {
    const params = {
        Bucket: process.env.S3_FILE_BUCKET,
        Key: key, // File name you want to save as in S3
        Body: file,
        ContentType : 'image/jpeg'
    };
    // Uploading files to the bucket
    s3.upload(params, async function(err, data) {
        if (err) {
            throw err;
        }  
    });
  };

  function makeid(length) {
    var result           = '';
    var characters       = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
    var charactersLength = characters.length;
    for ( var i = 0; i < length; i++ ) {
       result += characters.charAt(Math.floor(Math.random() * charactersLength));
    }
    return result;
  }

  async function getNextSequenceValue(sequenceName){
    try {
      const data = await AutoGenerator.findOne({id: sequenceName},{incNo:1,_id:0});
      if(!data){
        const sessionData = new AutoGenerator({
          id: sequenceName,
          incNo: 1000000,
        });
        await sessionData.save();
        return 1000000;
      }
      let incNo = data.incNo < 1000000 ? 1000000 : data.incNo+1;
      await AutoGenerator.updateOne({id: sequenceName},{$set:{incNo:incNo}});
      return incNo;
    } catch(err){
      throw err
    }
  }

  function messageBuilder(res, status, InputParams, msg, data = {}) {
    try {
        return res.status(status).json({
            InputParams,
            Response: { status, msg, ...data },
        });
    } catch (err) {
        throw err;
    }
  }

async function uploadExcel(file, key) {
    const params = {
        Bucket: process.env.S3_FILE_BUCKET,
        Key: key, // File name you want to save as in S3
        Body: file
    };
    // Uploading files to the bucket
    s3.upload(params, async function (err, data) {
        if (err) {
            throw err;
        }
         
        return true;
    });
};

class CommonDataFormator{
  constructor(merchantId){
    this.merchantId = merchantId;
  }
  setMerchantId(merchantId){
    this.merchantId = merchantId;
    return true;
  }
  async isSubscribed(id,merchantId){
    if(!mongoose.isValidObjectId(id) || !mongoose.isValidObjectId(merchantId)) {
      return false;
    }
    return (await ShopperrSubscribeProducts.findOne({
      mId: mongoose.Types.ObjectId(merchantId),
      pId: mongoose.Types.ObjectId(id),
    }) ? true : false);
  }
  imgDataModifier(imgUrl,length=3,params={}){ 
    let size = (imgUrl.length || 0);
    length = (parseInt(length) ?? 3)
    length = length > size ? size : length;
    let result = [];
    do{
      let src = imgUrl[result.length];
      let otherData = {};
      if(typeof imgUrl[result.length] == "object"){
        otherData = src;
        src = src.src;
        delete otherData.src;
      }  
      if(params.varient_id && params.varient_id == otherData?.varient_id){
        result.unshift({
          src: `${process.env.S3_BUCKET_FILE_URL}/${src}`,
          ...otherData
        });
        continue;
      }
      result.push({
        src: `${process.env.S3_BUCKET_FILE_URL}/${src}`,
        ...otherData
      });
    }while(result.length < length);
    return result;
  }
  prepareVD(variantDesc){
    if(!variantDesc?.length){
      return [];
    }
    const variantDescriptionObj = variantDesc.map((item) => {
      const makeobject = item.replace(/(\b\S+\b)=(\b\S+\b)/g, '"$1":"$2"');
      const obj = JSON.parse(makeobject);
      return obj;
    });
    return variantDescriptionObj.map(
      ({ price, mrp, sp, quantity, sellingPrice, cogs, ...other }) => {
        return {
          ...other,
          price: parseFloat(new Number(price).toFixed(2)),
          mrp: parseFloat(new Number(mrp).toFixed(2)),
          sp: parseFloat(new Number(sp).toFixed(2)),
          sellingPrice: parseFloat(new Number(sellingPrice).toFixed(2)),
          quantity: parseInt(quantity),
        };
      }
    );
  }
  prepareVO(variantOptions){
    if (!variantOptions?.length > 0) {
      return [];
    }
    return variantOptions?.map((obj) => {
        const removeBraces = obj.substring(1, obj.length - 1);
        const objkeypair = removeBraces.replace(/=/g, ":").replace(/ /g, "");
        const obje = objkeypair.substring(
          objkeypair.indexOf("name") + 5,
          objkeypair.indexOf("values") - 1
        );
        const value = objkeypair.substring(
          objkeypair.indexOf("values") + 7,
          objkeypair.indexOf("]") + 1
        );
        return {
          name: obje,
          values: value.replace(/[\[\]']+/g, "").split(","),
        };
    }) || [];
  }
  setFirstSelectedVarient(vo){
    return vo?.map(
      ({ values, ...otherValues }, index) => {
        //remove space from varient
        const firstSelected = values[0];
        return {
          ...otherValues,
          values,
          defaultSelected: firstSelected,
        };
      }
    ) || [];
  }
  getVariantCombination(vd){
    return vd?.map(({ varient, ...otherValues }) => {
        //remove space from varientCom
        return {
          ...otherValues,
          varient,
          varientCombination:varient.split("/").map((v) => v.trim()),
        };
      }
    ) || [];
  }
  findProductVariant(vd,sku){
    return vd?.find((variant) => {
      return variant.sku == sku;
    }) || null;
  }
}

class ProductAlgoPrices{
  priceAlgo = "ds";
  constructor(product,algo){
    this.product = product;
    this.priceAlgo = algo;
    this.shipping = "ex-china";
  }
  setShippingMethod(shipping){
    this.shipping = shipping;
    return this;
  }
  setProduct(product){
    this.product = product;
    return this;
  }
  setPriceAlgo(algo){
    this.priceAlgo = algo;
    return this;
  }
  async getPriceObj(){
    let priceObj = null; 
    let netAmount = 0;
    let gst = 0;
    let total_duty = 0;
    switch(this.priceAlgo){
      case "ds":
        priceObj = await this.getPrices();
        netAmount = (100 / (parseFloat(this.product.igst || 18) + 100)) * parseFloat(priceObj.dropshipperPrice.price);
        gst = parseFloat(priceObj.dropshipperPrice.price) - netAmount;
        return {
          ...priceObj.dropshipperPrice,
          netAmount,
          gst,
          shippingCost:0,
          total_duty:0
        }
      case "global":
        let globalPrice = getGlobalPriceD({
          fp:slabPrice(productObj.price,cpObj.quantity,isVariant,productObj),
          pw:productObj?.weight || 0,
          bcd:productObj?.bcd || 10,
          swc:productObj?.swcOnBcd || 10,
          pmargin:productObj?.productMargin || 40,
          igst:Number(igst) || 18
        })
       
        let shippingCost = getGlobalShipping({fp:productObj.price,pw:productObj.weight})[this.shipping] || 0;
        if(shipping !== 'ex-china'){
          netAmount = (100 / (parseFloat(this.product.igst || 18) + 100)) * parseFloat(priceObj.price);
          gst = parseFloat(sellingPrice) - netAmount;
          total_duty = (globalPrice.duty* parseInt(cpObj.quantity))
        }

        return {
          ...globalPrice,
          netAmount,
          gst,
          shippingCost,
          total_duty
        }
      default:
        priceObj = await this.getPrices();
        netAmount = (100 / (parseFloat(this.product?.igst || 18) + 100)) * parseFloat(priceObj.dropshipperPrice.price);
        gst = parseFloat(priceObj.dropshipperPrice.price) - netAmount;
        return {
          ...priceObj.dropshipperPrice,
          netAmount,
          gst,
          shippingCost:0,
          total_duty:0
        }
    }
  }
  async getPrices(){
    let supplier = await User.findOne({_id : mongoose.Types.ObjectId(this.product.supplier_id)},{price_algo:1});      
    let suppllierOrigin = '';
    if(supplier){
      suppllierOrigin = supplier.price_algo;
    }
    
    let fp      =  this.product['price'];
    let mrps    = (this.product.mrp != '') ? this.product.mrp : 0;
    let pw      = (this.product.weight != '') ? this.product.weight : 0;
    let lenght  = ( this.product.length != '') ? this.product.length : 0;
    let width   = (this.product.width != '') ? this.product.width : 0;
    let height  = (this.product.height != '') ? this.product.height : 0;
    let pbcd    = (this.product.bcd != undefined) ? this.product.bcd : 10; 
    let pigst   = (this.product.igst != undefined) ? this.product.igst : 18;
    let retailerMargin   = (this.product.productMargin != undefined) ? this.product.productMargin : 40;
    let pswc    = (this.product['swcOnBcd'] != undefined) ? this.product['swcOnBcd'] : 10; 
    return await updateShopperrPriceAlgo(Number(fp) , Number(pw) , suppllierOrigin , pbcd , pigst , pswc , lenght , width , height , mrps , retailerMargin);
  }
}

class ManageCart extends CommonDataFormator{
  constructor(cartProducts,params){
    super(params.merchant._id);
    this.merchant = params.merchant;
    this.productModal = params.productModal;
    this.cartProducts = cartProducts;
    this.algoObj = new ProductAlgoPrices("","");
    this.priceRule = null;
    this.customerPrices = {};
  }
  setAlgoMethod(algoObj){
    this.algoObj = algoObj;
    return this;
  }
  onCheckout(){
    this.oncheckout = true;
    return this;
  }
  setPriceRule(priceRule){ 
    this.priceRule = priceRule;
    return this;
  }
  setCustomerPrices(customerPrices){
    this.customerPrices = customerPrices;
    return this;
  }
  formatMarchant(){
    return {
      email: this.merchant.email,
      first_name: this.merchant.firstName,
      last_name: this.merchant.lastName,
      accepts_marketing: false,
      created_at: new Date().toISOString(),
      updated_on: new Date().toISOString(),
      phone: this.merchant.phoneNo,
      currency: "INR",
      verified_email: false,
      tax_exempt: false,
      accepts_marketing: false,
    }
  }
  buildSet(price,currency="INR"){
    return {
      shop_money: {
        amount: price,
        currency_code: currency,
      },
    }
  }
  formatCartDataForView(productObj){
    productObj.title = productObj.name;
    productObj.total_amount = Math.ceil(productObj.total_amount).toFixed(2);
    productObj.total_gst = Number(productObj.total_gst).toFixed(2);
    productObj.total_shipping_cost = Number(productObj.total_shipping_cost).toFixed(2);
    productObj.total_duty = Number(productObj.total_duty).toFixed(2);
    productObj.price=Number(((parseFloat(productObj.total_amount)+parseFloat(productObj.total_gst))/productObj.cartQuantity).toFixed(2));
    return productObj;
  }
  formatCartDataForCheckout(productObj){
    //g(productObj);
    if(productObj && productObj.imgUrl[0] && productObj.imgUrl[0].src){
      productObj.src = `${process.env.S3_BUCKET_FILE_URL}/${productObj.imgUrl[0].src}`;
      delete productObj.imgUrl;
    } else {
      productObj.src = '';
    }

    productObj.title = productObj.name;
    productObj.price = Math.ceil(productObj.total_amount).toFixed(2);
    productObj.price_set = this.buildSet(productObj.price,"INR");

    productObj.total_gst = productObj.total_gst.toFixed(2);
    productObj.total_gst_set = this.buildSet(productObj.total_gst,"INR");

    productObj.total_shipping_cost = productObj.total_shipping_cost.toFixed(2);
    productObj.total_shipping_cost_set = this.buildSet(productObj.total_shipping_cost,"INR");

    productObj.total_discount = productObj.total_discount.toFixed(2);
    productObj.total_discount_set = this.buildSet(productObj.total_discount,"INR");

    productObj.quantity = productObj.quantity;
    productObj.requires_shipping = true;

    productObj.customer_price = (this.customerPrices?.[productObj.code]?.price || Number(productObj.price)).toFixed(2);
    productObj.price=((parseFloat(productObj.total_amount)+parseFloat(productObj.total_gst))/productObj.cartQuantity).toFixed(2);
    productObj.total_amount = Number(Math.ceil(productObj.total_amount).toFixed(2));

    return productObj;
  }
  getRequiredFields(productObj){
    let requiredFields = ['options','varientArray','skus',"vo" ,"bcd","seaPrice","swcOnBcd","igst","deliveryDaysFrom","deliveryDaysTo","warranty" ,"subtitle","so","st","stt", "sf", "paso", "past","pastt","pasf","spData","supplier_id","sid","customfields","bno","catId","cid", "ibat","iliu","invoicedesc","is_display","marketPlaceMrp","marketPlacePrice","marketPlaceUrl","mu", "nfi","pex" ,"pincl","price_update_flag","yfmf","pd_status","is_amazon_templete","taggedSuppliers","shippingCharge","hsn","barcode","channel","handle","mrp",
    "sp","cbm","description","id","pd_manage_status","vd"];
    let result = {};
    for(let key of requiredFields){
      if(productObj[key]){
        delete productObj[key];
      }
    }
    return productObj;
  }
  calculateDiscount(totalPrice, quantity) {
    if (!this.priceRule) {
      return false;
    }
    const subtotalRange = this.priceRule[mongooseConstantValues.PREREQUISITE_SUBTOTAL_RANGE];
    const quantityRange = this.priceRule[mongooseConstantValues.PREREQUISITE_QUANTITY_RANGE];
    const valueType = this.priceRule[mongooseConstantValues.VALUE_TYPE];
    const value = parseFloat(this.priceRule[mongooseConstantValues.VALUE]);
    let totalAmount = parseFloat(totalPrice * quantity);
    if (quantityRange && quantity > quantityRange) {
      return false;
    } else if (
      valueType == "fixed_amount" ||
      totalAmount < value ||
      (subtotalRange && totalAmount > subtotalRange)
    ) {
      return false;
    }
    totalAmount = parseFloat(totalPrice);
  
    let amountAfterDiscount = totalAmount;
    let discountAmount = 0;
    let perctVal = null;
    if (valueType == "fixed_amount") {
      amountAfterDiscount = totalAmount - value;
      discountAmount = value;
    } else {
      perctVal = Math.abs(parseFloat(value));
      discountAmount = (perctVal * totalAmount) / 100;
      amountAfterDiscount = totalAmount - discountAmount;
    }
    return {
      amountAfterDiscount,
      discountAmount,
      discountType: valueType,
      discountPercentValue: perctVal,
    };
  }

  async calculateCartPrice() {
    
    let totalGst = 0;
    let totalPrice = 0;
    let totalShippingCost = 0;
    let totalQuntity = 0;
    let totalDiscount = 0;
    let totalDuty = 0;
    let isCouponApplied = 0;
    
    let cartproducts=[];
    
    for (const product of this.cartProducts) {
      let productObj = await this.productModal.findOne({ _id: { $in: product.productId } },
        {
          barcodes:0,bpt:0,tags:0,pd_manage_status:0,uc_status:0,yfmf:0,price_update_flag:0,pd_status:0
        });

      if (!productObj) { 
        continue;
      }
      productObj = productObj.toJSON(); 
      productObj.cartQuantity = parseInt(product.quantity);

      let vd = this.findProductVariant(productObj.vd,product.sku);
      let varient_id = "";
      if(vd){
        // delete productObj.vd;
        // vd.code = vd.sku;
        // delete vd.sku;
        // productObj = { ...productObj, ...vd }; 
        productObj.price = vd.price;
        productObj.mrp = vd.mrp;
        productObj.code = vd.sku;
        productObj.sku = vd.sku;
        varient_id = vd.varient_id;
      }
      productObj.id = productObj._id.toString();


      let discountData = this.calculateDiscount(parseFloat(productObj.price),product.quantity);
      productObj.total_discount = 0;
      if (discountData) {
        productObj.price = discountData.amountAfterDiscount;
        productObj.total_discount = discountData.discountAmount;
        isCouponApplied = 1;
      }
      
      /* price Algo Start */
      let sp  = await this.algoObj.setProduct(productObj).getPriceObj(); 
      /* price Algo End */

      productObj.price = sp.price;
      totalQuntity += parseInt(product.quantity); 
      productObj.total_amount = sp.netAmount * parseInt(product.quantity);
      productObj.total_gst = sp.gst * parseInt(product.quantity);
      productObj.total_shipping_cost = sp.shippingCost * parseInt(product.quantity);
      productObj.total_duty = sp.total_duty * parseInt(product.quantity);
      
      totalDuty += productObj.total_duty;
      totalPrice += productObj.total_amount;
      totalGst += productObj.total_gst;
      totalShippingCost += productObj.total_shipping_cost;
      totalDiscount += productObj.total_discount;
      
      if(this.oncheckout){
        productObj = this.formatCartDataForCheckout(productObj);
      } else {
        productObj = this.formatCartDataForView(productObj);
        productObj.imgUrl = this.imgDataModifier(productObj.imgUrl,productObj.imgUrl.length-1,{varient_id});
      }

      productObj.quantity = productObj.cartQuantity;
      
      
      let vendorName = '';
      if(productObj.spData == undefined){
        vendorName = 'SFC Inc.';
        
      } else {
        vendorName = productObj.spData && productObj.spData.name ? productObj.spData.name : ''
        
      }
      
      productObj.vendor = vendorName;
      
    
      productObj.commission=Number(((Number(this.customerPrices?.[productObj.code]?.price || productObj.price)-Number(productObj.price))*productObj.cartQuantity).toFixed(2));

      if(this.oncheckout){
        productObj = this.getRequiredFields(productObj);
      }
      
      cartproducts.push(
        productObj
      );
    }
    const result = {
      products: cartproducts,
      totalShippingCost,
      totalGst,
      totalPrice,
      totalQuntity,
      totalDuty,
      totalDiscount,
      isCouponApplied
    }
    return {
      getcartViewData:()=>this.getcartViewData(result),
      getResultData: result
    };
  }  

  getDiscountCodes(){
    return [
      {
        target_type: this.priceRule[mongooseConstantValues.TARGET_TYPE],
        type: "manual",
        value: this.priceRule[mongooseConstantValues.VALUE],
        value_type: this.priceRule[mongooseConstantValues.VALUE_TYPE],
        allocation_method: "across",
        target_selection: this.priceRule[mongooseConstantValues.TARGET_SELECTION],
        title: this.priceRule[mongooseConstantValues.TITLE],
        description: this.priceRule[mongooseConstantValues.TITLE],
      }
    ]
  }
  getcartViewData(cartData){
    return {
      products: cartData.products,
      grossAmount: (cartData.totalPrice + cartData.totalShippingCost + cartData.totalGst + cartData.totalDuty).toFixed(2),
      shippingCharges: cartData.totalShippingCost.toFixed(2),
      GST: cartData.totalGst.toFixed(2),
      netAmount: cartData.totalPrice.toFixed(2),
      nproducts: cartData.products.length,
      totalItems: cartData.totalQuntity,
      totalDuty: cartData.totalDuty
    };
  }
  getcartCheckoutData(cartData){
    return {
      products: cartData.products,
      grossAmount: (cartData.totalPrice + cartData.totalShippingCost + cartData.totalGst + cartData.totalDuty).toFixed(2),
      shippingCharges: cartData.totalShippingCost.toFixed(2),
      GST: cartData.totalGst.toFixed(2),
      netAmount: cartData.totalPrice.toFixed(2),
      nproducts: cartData.products.length,
      totalItems: cartData.totalQuntity,
      totalDuty: cartData.totalDuty
    }
  }
}

  async function getProductInfobyProductId(algo,product,sku){ 
    const algoObj=new ProductAlgoPrices(product,"")
        let productArray    = product;
        productArray = JSON.parse(JSON.stringify(productArray));
        if(sku && productArray.vd){
          let vd = productArray.vd.find((v)=>v.sku == sku);
          if(vd){
            productArray.price = vd.price;
            productArray.mrp = vd.mrp;
          }
        }
        let sp =await algoObj.setProduct(productArray).getPrices();
         let fp      =  productArray['price']; 
         let pigst   = (productArray.igst != undefined) ? productArray.igst : 18;
        let retailerMargin   = (productArray.productMargin != undefined) ? productArray.productMargin : 40;
        let amazonprice = (productArray.marketPlacePrice != undefined) ? productArray.marketPlacePrice : 0;
        let amazonmrp = (productArray.marketPlaceMrp != undefined) ? productArray.marketPlaceMrp : 0;
        let marketPlaceUrl = (productArray.marketPlaceUrl != undefined) ? productArray.marketPlaceUrl : "No Data Found.";  
        let response = { 
          airPrice:{
            factoryPrice : fp,
            price : sp.airPrice.price,
            cogs  : sp.airPrice.cogs,
            mrp   : productArray.pmrp ? productArray.pmrp : (((Math.floor(((sp.airPrice.mrp) ? sp.airPrice.mrp*2 : 0).toFixed(2)/100))*100) + 99),
            priceWithoutGst : (sp.airPrice.priceWithoutGst),
            gstOnProduct    : new Number((sp.airPrice.price - sp.airPrice.priceWithoutGst).toFixed(2)),
            retailerMargin  : new Number(retailerMargin.toFixed(2)),
            retailerMarginPrice : new Number((sp.airPrice.cogs*retailerMargin/100).toFixed(2)),
            amazonprice : amazonprice,
            amazonmrp : amazonmrp,
            amazonMarketPlaceUrl : marketPlaceUrl,
            gstPer : pigst
          },
          dropshipperPrice:{
            factoryPrice : fp,
            price : sp.dropshipperPrice.price,
            cogs  : sp.dropshipperPrice.cogs,
            mrp   : productArray.pmrp ? productArray.pmrp : (((Math.floor(((sp.dropshipperPrice.mrp) ? sp.dropshipperPrice.mrp*2 : 0).toFixed(2)/100))*100) + 99),
            priceWithoutGst : (sp.dropshipperPrice.priceWithoutGst),
            gstOnProduct    : new Number((sp.dropshipperPrice.price - sp.dropshipperPrice.priceWithoutGst).toFixed(2)),
            retailerMargin  : new Number(retailerMargin.toFixed(2)),
            retailerMarginPrice : new Number((sp.dropshipperPrice.cogs*retailerMargin/100).toFixed(2)),
            amazonprice : amazonprice,
            amazonmrp : amazonmrp,
            amazonMarketPlaceUrl : marketPlaceUrl,
            gstPer : pigst
          },
          seaPrice:{
            factoryPrice : fp,
            price : sp.seaPrice.price,
            cogs  : sp.seaPrice.cogs,
            mrp   : productArray.pmrp ? productArray.pmrp : (((Math.floor(((sp.seaPrice.mrp) ? sp.seaPrice.mrp*2 : 0).toFixed(2)/100))*100) + 99),
            priceWithoutGst : (sp.seaPrice.priceWithoutGst),
            gstOnProduct    : new Number((sp.seaPrice.price - sp.seaPrice.priceWithoutGst).toFixed(2)),
            retailerMargin  : new Number(retailerMargin.toFixed(2)),
            retailerMarginPrice : new Number((sp.seaPrice.cogs*retailerMargin/100).toFixed(2)),
            amazonprice : amazonprice,
            amazonmrp : amazonmrp,
            amazonMarketPlaceUrl : marketPlaceUrl,
            gstPer : pigst
          }
        }  
        return response; 
}

module.exports = { addMerchantSubscribedProductCron,upload_image,makeid,getNextSequenceValue,messageBuilder,uploadExcel,CommonDataFormator,ProductAlgoPrices,ManageCart,getProductInfobyProductId}