diff --git a/src/controller/item.controller.js b/src/controller/item.controller.js index fc5683e..d5f2ee5 100644 --- a/src/controller/item.controller.js +++ b/src/controller/item.controller.js @@ -2,6 +2,18 @@ const mongoose = require("mongoose"); const Item = require("../models/Item"); const WidgetFamily = require("../models/WidgetFamily"); const Inventory = require("../models/Inventory"); +const { + PickItemTransaction, + PutItemTransaction, + ReserveItemTransaction, + // CheckInItemTransaction, + // CheckOutItemTransaction, + // ReportItemTransaction, + // AdjustItemTransaction, +} = require("../models/ItemTransaction"); + +const ItemAssociation = require("../models/ItemAssociation"); +const Sublevel = require("../models/Sublevel"); const { InventoryTypes } = require("../config/constants"); module.exports = { @@ -195,13 +207,115 @@ module.exports = { } }, pickItem: async (req, res, next) => { - res.status(500).send({ success: false, error: "Not Implemented" }); + try { + const { id } = req.params; + if (!id || mongoose.isValidObjectId(id)) { + res.status(400).send("Missing/Invalid id param"); + return; + } + + const item = await Item.findById(id); + if (!item) { + res.status(404).send("item not found"); + return; + } + + const { putQuantity, subLevel } = req.body; + if (!(putQuantity && putQuantity > 0) || !(subLevel && mongoose.isValidObjectId(subLevel))) { + res.status(400).send("Invalid value for putQuantity/subLevel"); + return; + } + + const subLevelObj = await Sublevel.findById(subLevel); + const itemAssociation = await ItemAssociation.findOne({ item_id: item._id, sub_level_id: subLevelObj._id }); + itemAssociation.totalQuantity = itemAssociation.totalQuantity + putQuantity; + itemAssociation.availableQuantity = itemAssociation.availableQuantity + putQuantity; + await itemAssociation.save(); + + await PickItemTransaction.create({ + type: "PICK", + performedOn: item, + performedBy: res.locals.user, + putQuantity: putQuantity, + subLevel: subLevelObj, + }); + } catch (error) { + next(error); + } }, putItem: async (req, res, next) => { - res.status(500).send({ success: false, error: "Not Implemented" }); + try { + const { id } = req.params; + if (!id || mongoose.isValidObjectId(id)) { + res.status(400).send("Missing/Invalid id param"); + return; + } + + const item = await Item.findById(id); + if (!item) { + res.status(404).send("item not found"); + return; + } + + const { pickupQuantity, subLevel } = req.body; + if (!(pickupQuantity && pickupQuantity > 0) || !(subLevel && mongoose.isValidObjectId(subLevel))) { + res.status(400).send("Invalid value for pickupQuantity/subLevel"); + return; + } + + const subLevelObj = await Sublevel.findById(subLevel); + const itemAssociation = await ItemAssociation.findOne({ item_id: item._id, sub_level_id: subLevelObj._id }); + itemAssociation.totalQuantity = itemAssociation.totalQuantity - pickupQuantity; + itemAssociation.availableQuantity = itemAssociation.availableQuantity - pickupQuantity; + await itemAssociation.save(); + + await PutItemTransaction.create({ + type: "PUT", + performedOn: item, + performedBy: res.locals.user, + pickupQuantity: pickupQuantity, + subLevel: subLevelObj, + }); + } catch (error) { + next(error); + } }, reserveItem: async (req, res, next) => { - res.status(500).send({ success: false, error: "Not Implemented" }); + try { + const { id } = req.params; + if (!id || mongoose.isValidObjectId(id)) { + res.status(400).send("Missing/Invalid id param"); + return; + } + + const item = await Item.findById(id); + if (!item) { + res.status(404).send("item not found"); + return; + } + + const { reserveQuantity, job, pickupDate } = req.body; + if (!(reserveQuantity && reserveQuantity > 0) || !(job && mongoose.isValidObjectId(job)) || !(pickupDate && Date.parse(pickupDate))) { + res.status(400).send("Invalid value for reserveQuantity/job/pickupDate"); + return; + } + + const itemAssociation = await ItemAssociation.findOne({ item_id: item._id, availableQuantity: { $gte: reserveQuantity } }); + itemAssociation.reservedQuantity = itemAssociation.reservedQuantity + reserveQuantity; + itemAssociation.availableQuantity = itemAssociation.availableQuantity - reserveQuantity; + await itemAssociation.save(); + + await ReserveItemTransaction.create({ + type: "PUT", + performedOn: item, + performedBy: res.locals.user, + reserveQuantity: reserveQuantity, + job: job, + pickupDate: Date.parse(pickupDate), + }); + } catch (error) { + next(error); + } }, checkInItem: async (req, res, next) => { res.status(500).send({ success: false, error: "Not Implemented" }); diff --git a/src/controller/item.router.js b/src/controller/item.router.js index 174f0b1..83e4b94 100644 --- a/src/controller/item.router.js +++ b/src/controller/item.router.js @@ -1,6 +1,6 @@ const router = require("express").Router(); const controller = require("./item.controller"); -const { ItemTransactionCheck } = require("./utils/authorize"); +const { AuthenticateMiddleware, ItemTransactionCheck } = require("./utils/authorize"); /** * @route /item/ */ @@ -24,36 +24,36 @@ router.get("/:id", controller.getItemByID); /** * @route /item/:id/pick */ -router.post("/:id/pick", ItemTransactionCheck, controller.pickItem); +router.post("/:id/pick", AuthenticateMiddleware, ItemTransactionCheck, controller.pickItem); /** * @route /item/:id/put */ -router.post("/:id/put", ItemTransactionCheck, controller.putItem); +router.post("/:id/put", AuthenticateMiddleware, ItemTransactionCheck, controller.putItem); /** * @route /item/:id/reserve */ -router.post("/:id/reserve", ItemTransactionCheck, controller.reserveItem); +router.post("/:id/reserve", AuthenticateMiddleware, ItemTransactionCheck, controller.reserveItem); /** * @route /item/:id/check-in */ -router.post("/:id/check-in", ItemTransactionCheck, controller.checkInItem); +router.post("/:id/check-in", AuthenticateMiddleware, ItemTransactionCheck, controller.checkInItem); /** * @route /item/:id/check-out */ -router.post("/:id/check-out", ItemTransactionCheck, controller.checkOutItem); +router.post("/:id/check-out", AuthenticateMiddleware, ItemTransactionCheck, controller.checkOutItem); /** * @route /item/:id/report */ -router.post("/:id/report", ItemTransactionCheck, controller.reportItem); +router.post("/:id/report", AuthenticateMiddleware, ItemTransactionCheck, controller.reportItem); /** * @route /item/:id/adjust */ -router.post("/:id/adjust", ItemTransactionCheck, controller.adjustItem); +router.post("/:id/adjust", AuthenticateMiddleware, ItemTransactionCheck, controller.adjustItem); module.exports = router; diff --git a/src/models/ItemAssociation.js b/src/models/ItemAssociation.js index e84cc94..448e465 100644 --- a/src/models/ItemAssociation.js +++ b/src/models/ItemAssociation.js @@ -10,7 +10,15 @@ const schema = new mongoose.Schema( type: mongoose.Schema.Types.ObjectId, ref: "Sublevel", }, - quantity: { + totalQuantity: { + type: Number, + default: 0, + }, + reservedQuantity: { + type: Number, + default: 0, + }, + availableQuantity: { type: Number, default: 0, }, diff --git a/src/models/ItemTransaction.js b/src/models/ItemTransaction.js index e955756..708e7bd 100644 --- a/src/models/ItemTransaction.js +++ b/src/models/ItemTransaction.js @@ -33,6 +33,10 @@ const PutItemTransaction = ItemTransaction.discriminator( type: Number, required: true, }, + subLevel: { + type: mongoose.Schema.Types.ObjectId, + ref: "Sublevel" + }, }) ); @@ -43,6 +47,10 @@ const PickItemTransaction = ItemTransaction.discriminator( type: Number, required: true, }, + subLevel: { + type: mongoose.Schema.Types.ObjectId, + ref: "Sublevel", + }, }) );