diff --git a/config/baseSchema.json b/config/baseSchema.json index 25e6e18..7d9ccee 100644 --- a/config/baseSchema.json +++ b/config/baseSchema.json @@ -97,6 +97,10 @@ }, "env": { "type": "string" + }, + "trackStock": { + "type": "boolean", + "default": false } }, "required": [ diff --git a/config/settings.json b/config/settings.json index f59eb2a..36fcd51 100644 --- a/config/settings.json +++ b/config/settings.json @@ -22,5 +22,6 @@ "currencySymbol": "£", "paymentGateway": "stripe", "databaseConnectionString": "mongodb://127.0.0.1:27017/expresscart", - "theme": "Cloth" + "theme": "Cloth", + "trackStock": true } diff --git a/routes/index.js b/routes/index.js index 9ca7de0..3520c74 100644 --- a/routes/index.js +++ b/routes/index.js @@ -11,16 +11,37 @@ router.get('/payment/:orderId', async (req, res, next) => { let config = req.app.config; // render the payment complete message - db.orders.findOne({_id: common.getId(req.params.orderId)}, async (err, result) => { + db.orders.findOne({_id: common.getId(req.params.orderId)}, async (err, order) => { if(err){ console.info(err.stack); } + + // If stock management is turned on payment approved update stock level + if(config.trackStock && req.session.paymentApproved){ + order.orderProducts.forEach(async (product) => { + const dbProduct = await db.products.findOne({_id: common.getId(product.productId)}); + let newStockLevel = dbProduct.productStock - product.quantity; + if(newStockLevel < 1){ + newStockLevel = 0; + } + + // Update product stock + await db.products.update({ + _id: common.getId(product.productId) + }, { + $set: { + productStock: newStockLevel + } + }, {multi: false}); + }); + } + res.render(`${config.themeViews}payment_complete`, { title: 'Payment complete', config: req.app.config, session: req.session, pageCloseBtn: common.showCartCloseBtn('payment'), - result: result, + result: order, message: common.clearSessionValue(req.session, 'message'), messageType: common.clearSessionValue(req.session, 'messageType'), helpers: req.handlebars.helpers, @@ -217,6 +238,7 @@ router.post('/product/emptycart', (req, res, next) => { // Add item to cart router.post('/product/addtocart', (req, res, next) => { const db = req.app.db; + const config = req.app.config; let productQuantity = req.body.productQuantity ? parseInt(req.body.productQuantity) : 1; const productComment = req.body.productComment ? req.body.productComment : null; @@ -242,6 +264,13 @@ router.post('/product/addtocart', (req, res, next) => { return res.status(400).json({message: 'Error updating cart. Please try again.'}); } + // If stock management on check there is sufficient stock for this product + if(config.trackStock){ + if(productQuantity > product.productStock){ + return res.status(400).json({message: 'There is insufficient stock of this product.'}); + } + } + let productPrice = parseFloat(product.productPrice).toFixed(2); // Doc used to test if existing in the cart with the options. If not found, we add new. diff --git a/routes/order.js b/routes/order.js index b0bd266..d26dd08 100644 --- a/routes/order.js +++ b/routes/order.js @@ -61,7 +61,6 @@ router.get('/admin/order/view/:id', common.restrict, (req, res) => { if(err){ console.info(err.stack); } - res.render('order', { title: 'View order', result: result, diff --git a/routes/product.js b/routes/product.js index d2fac28..0e1be0f 100644 --- a/routes/product.js +++ b/routes/product.js @@ -212,6 +212,7 @@ router.post('/admin/product/update', common.restrict, common.checkAccess, (req, req.session.productTags = req.body.frmProductTags; req.session.productOptions = req.body.productOptJson; req.session.productComment = common.checkboxBool(req.body.frmProductComment); + req.session.productStock = req.body.frmProductStock ? req.body.frmProductStock : null; // redirect to insert res.redirect('/admin/product/edit/' + req.body.frmProductId); @@ -225,11 +226,10 @@ router.post('/admin/product/update', common.restrict, common.checkAccess, (req, productPermalink: req.body.frmProductPermalink, productTags: common.cleanHtml(req.body.frmProductTags), productOptions: common.cleanHtml(req.body.productOptJson), - productComment: common.checkboxBool(req.body.frmProductComment) + productComment: common.checkboxBool(req.body.frmProductComment), + productStock: req.body.frmProductStock ? parseInt(req.body.frmProductStock) : null }; - console.log('test', productDoc); - // if no featured image if(!product.productImage){ if(images.length > 0){ diff --git a/views/product_edit.hbs b/views/product_edit.hbs index 38eff52..f833009 100644 --- a/views/product_edit.hbs +++ b/views/product_edit.hbs @@ -33,6 +33,12 @@ +
+ +
+ +
+