const Cart_Item = require('../models/user/Cart_item') const Order = require('../models/user/Order') const User = require('../models/user/User') const localeController = require('./localeController') const Product = require('../models/product/Product') const {body, validationResult} = require('express-validator') const dateformat = require('dateformat') const v_m = require('../validation_messages') ////////////////////////////////////// cart module.exports.addToCart = [ [ body('user_id') .custom((value, {req}) => { return User.findById(value) .then(user => { if (user) return true }) .catch(err => { return Promise.reject(v_m[req.body.locale].not_found.user_id) }) }), body('product_id') .custom((value, {req}) => { return Product.findById(value) .then(product => { if (product) return true }) .catch(err => { return Promise.reject(v_m[req.body.locale].not_found.item_id) }) }), body('quantity') .notEmpty() .withMessage((value, {req}) => { return v_m[req.body.locale].required.quantity }) .bail() .isNumeric() .withMessage((value, {req}) => { return v_m[req.body.locale].format.number }) ], (req, res) => { const errors = validationResult(req) if (!errors.isEmpty()) return res.status(422).json(errors) Cart_Item.findOne({product_id: req.body.product_id, user_id: req.body.user_id}) .then(item => { item.quantity = Number(item.quantity) + Number(req.body.quantity) item.updated_at = dateformat(Date.now(), 'yyyy-mm-dd HH:MM:ss') item.markModified('quantity') item.markModified('updated_at') item.save() return res.json({message: v_m[req.body.locale].response.success_save}) }) .catch(err => { const data = { user_id: req.body.user_id, product_id: req.body.product_id, quantity: req.body.quantity, created_at: dateformat(Date.now(), 'yyyy-mm-dd HH:MM:ss') } const cartItem = new Cart_Item(data) cartItem.save((err, data) => { if (err) console.log(err) return res.json({message: v_m[req.body.locale].response.success_save}) }) }) } ] module.exports.getCartItems = [ (req, res) => { Cart_Item.find({user_id: req.params.user_id}, (err, data) => { if (err) console.log(err) return res.json(data) }) } ] module.exports.updateCart = [ (req, res) => { Cart_Item.findById(req.params.item_id) .then(item => { item.quantity = Number(req.body.quantity) item.updated_at = dateformat(Date.now(), 'yyyy-mm-dd HH:MM:ss') item.markModified('quantity') item.markModified('updated_at') item.save() return res.json({message: v_m[req.body.locale].response.success_save}) }) .catch(err => { return res.status(404).json({message: v_m[req.body.locale].not_found.item_id}) }) } ] module.exports.deleteFromCart = [ (req, res) => { Cart_Item.findByIdAndDelete(req.params.item_id) .then(item => { Cart_Item.find({user_id: item.user_id}) .then(items => { return res.json(items) }) }) .catch(err => { return res.status(404).json({message: v_m['en'].not_found.item_id}) }) } ] ////////////////////////////////////// order module.exports.addOrder = [ [ body('user_id') .custom((value, {req}) => { return User.findById(value) .then(user => { return true }) .catch(err => { return Promise.reject(v_m[req.body.locale].not_found.user_id) }) }) ], //////////////////// validation step (req, res, next) => { Cart_Item.find({user_id: req.body.user_id}) .then(items => { // check if cart is not empty if (items.length) { // check product stock let outOfRun = [] items.forEach(async (item, index) => { await Product.findById(item.product_id) .then(product => { if (product.stock < item.quantity) { outOfRun.push({ product_id: product._id, category_id: product.category, stock: product.stock }) item.remove() } if (index + 1 === items.length) { if (!outOfRun.length) return next() else return res.status(422).json(outOfRun) } }) }) } else { return res.status(404).json({message: v_m[req.body.locale].response.cart_empty}) } }) }, //////////////////// save order (req, res) => { Cart_Item.find({user_id: req.body.user_id}) .then(items => { // save the order const orderData = { user_id: req.body.user_id, number: Date.now(), created_at: dateformat(Date.now(), 'yyyy-mm-dd HH:MM:ss') } const order = new Order(orderData) order.save((err, order) => { if (err) console.log(err) // get price unit for items let unit = localeController.locales.filter(item => { return item.value === req.body.locale })[0].currency // add incomplete status to order order.statuses.push({ status: 'incomplete', created_at: dateformat(Date.now(), 'yyyy-mm-dd HH:MM:ss') }) // add each item (Cart_Item result) to the order (saved Order result) and then remove it items.forEach((item, index) => { // get the price of each item depend on order locale Product.findById(item.product_id).then(product => { let data = { product_id: item.product_id, quantity: item.quantity, price: product.product_details[req.body.locale].price, price_unit: unit, created_at: dateformat(Date.now(), 'yyyy-mm-dd HH:MM:ss') } order.order_items.push(data) // reduce the product stock product.stock = Number(product.stock) - Number(item.quantity) product.save() item.remove() if (index + 1 === items.length) { order.save() return res.json(order) } }) }) }) }) .catch(err => { return res.status(500).json(err) }) } ] module.exports.addAddressToOrder = [ (req, res) => { Order.findById(req.params.order_id) .then(order => { if (!order.address) { User.findOne({'addresses._id': req.body.address_id}) .then(user => { order.address = user.addresses.id(req.body.address_id) // add processing status to order order.statuses.push({ status: 'processing', created_at: dateformat(Date.now(), 'yyyy-mm-dd HH:MM:ss') }) order.save() return res.json(order) }) .catch(err => { console.log(err) }) } else { return res.status(500).json({message: v_m[req.body.locale].response.already_has_address}) } }) .catch(err => { console.log(err) return res.status(404).json({message: v_m[req.body.locale].not_found.order_id}) }) } ] module.exports.addStatusToOrder = [ (req, res) => { Order.findById(req.params.order_id) .then(order => { order.statuses.push({ status: req.body.status, created_at: dateformat(Date.now(), 'yyyy-mm-dd HH:MM:ss') }) order.save() return res.json(order) }) .catch(err => { return res.status(500).json(err) }) } ] module.exports.getOrders = [ (req, res) => { Order.find({user_id: req.params.user_id}) .then(orders => { return res.json(orders) }) .catch(err => { return res.status(500).json(err) }) } ] module.exports.getOneOrder = [ (req, res) => { Order.findById(req.params.order_id) .then(order => { return res.json(order) }) .catch(err => { return res.status(500).json(err) }) } ] ////////////////////////////////////// get list of all orders for admin module.exports.getAllOrders = [ (req, res) => { Order.find({}) .then(orders => { return res.json(orders) }) .catch(err => { return res.status(500).json(err) }) } ]