diff --git a/backend/controllers/shop/sub-controllers/adminController.js b/backend/controllers/shop/sub-controllers/adminController.js deleted file mode 100644 index 61f9054d..00000000 --- a/backend/controllers/shop/sub-controllers/adminController.js +++ /dev/null @@ -1,44 +0,0 @@ -const Payment = require("../models/payment"); -const Invoice = require("../models/invoice"); - -// Admin view all payments -const adminViewPayments = async (req, res) => { - try { - const payments = await Payment.find() - .populate("orderId") - .populate("userId"); - res.status(200).json(payments); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -// Admin view all invoices -const adminViewInvoices = async (req, res) => { - try { - const invoices = await Invoice.find() - .populate("orderId") - .populate("userId"); - res.status(200).json(invoices); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -// Admin filter/sort payments -const adminFilterPayments = async (req, res) => { - const { status, startDate, endDate } = req.query; - const filters = {}; - if (status) filters.paymentStatus = status; - if (startDate && endDate) - filters.paymentDate = { $gte: startDate, $lte: endDate }; - - try { - const payments = await Payment.find(filters); - res.status(200).json(payments); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -module.exports = { adminViewPayments, adminViewInvoices, adminFilterPayments }; diff --git a/backend/controllers/shop/sub-controllers/agentController.js b/backend/controllers/shop/sub-controllers/agentController.js deleted file mode 100644 index ad4ac2a3..00000000 --- a/backend/controllers/shop/sub-controllers/agentController.js +++ /dev/null @@ -1,300 +0,0 @@ -const Agent = require("../../../model/shop/sub-model/Agent"); -const Ticket = require("../../../model/shop/sub-model/TIcket"); // Assuming Ticket model is defined - -// Create a new agent -exports.createAgent = async (req, res) => { - try { - const { name, email, role } = req.body; - - // Validate input - if (!name || !email || !role) { - return res - .status(400) - .json({ message: "Name, email, and role are required" }); - } - - // Check if email already exists - const existingAgent = await Agent.findOne({ email }); - if (existingAgent) { - return res - .status(400) - .json({ message: "Agent with this email already exists" }); - } - - const agent = new Agent({ name, email, role }); - await agent.save(); - - res.status(201).json({ message: "Agent created successfully", agent }); - } catch (err) { - res.status(500).json({ message: "Error creating agent", error: err }); - } -}; - -// Get all agents -exports.getAllAgents = async (req, res) => { - try { - const agents = await Agent.find(); - - if (agents.length === 0) { - return res.status(404).json({ message: "No agents found" }); - } - - res.status(200).json(agents); - } catch (err) { - res.status(500).json({ message: "Error fetching agents", error: err }); - } -}; - -// Get agent by ID -exports.getAgentById = async (req, res) => { - try { - const agent = await Agent.findById(req.params.id); - - if (!agent) { - return res.status(404).json({ message: "Agent not found" }); - } - - res.status(200).json(agent); - } catch (err) { - res.status(400).json({ message: "Invalid agent ID", error: err }); - } -}; - -// Update agent by ID -exports.updateAgent = async (req, res) => { - try { - const { name, email, role, status } = req.body; - - // Ensure at least one field to update is provided - if (!name && !email && !role && !status) { - return res.status(400).json({ message: "No fields provided to update" }); - } - - const agent = await Agent.findByIdAndUpdate( - req.params.id, - { name, email, role, status }, - { new: true, runValidators: true } - ); - - if (!agent) { - return res.status(404).json({ message: "Agent not found" }); - } - - res.status(200).json(agent); - } catch (err) { - res.status(500).json({ message: "Error updating agent", error: err }); - } -}; - -// Delete agent by ID -exports.deleteAgent = async (req, res) => { - try { - const agent = await Agent.findById(req.params.id); - - if (!agent) { - return res.status(404).json({ message: "Agent not found" }); - } - - // Ensure agent is not assigned to any active tickets before deletion - if (agent.assigned_tickets.length > 0) { - return res - .status(400) - .json({ - message: "Agent cannot be deleted as they have active tickets", - }); - } - - await Agent.findByIdAndDelete(req.params.id); - res.status(200).json({ message: "Agent deleted successfully" }); - } catch (err) { - res.status(500).json({ message: "Error deleting agent", error: err }); - } -}; - -// Assign a ticket to an agent -exports.assignTicketToAgent = async (req, res) => { - try { - const { ticketId } = req.body; - const agent = await Agent.findById(req.params.id); - const ticket = await Ticket.findById(ticketId); - - // Check if agent and ticket exist - if (!agent || !ticket) { - return res.status(404).json({ message: "Agent or Ticket not found" }); - } - - // Check if agent is inactive - if (agent.status === "inactive") { - return res - .status(400) - .json({ message: "Cannot assign ticket to an inactive agent" }); - } - - // Prevent assigning ticket if it is already assigned - if (ticket.status === "assigned") { - return res - .status(400) - .json({ message: "Ticket is already assigned to another agent" }); - } - - // Assign the ticket to the agent - agent.assigned_tickets.push(ticketId); - await agent.save(); - - // Update ticket status to 'assigned' - ticket.status = "assigned"; - await ticket.save(); - - res - .status(200) - .json({ message: "Ticket assigned to agent successfully", agent }); - } catch (err) { - res - .status(500) - .json({ message: "Error assigning ticket to agent", error: err }); - } -}; - -// Unassign a ticket from an agent -exports.unassignTicketFromAgent = async (req, res) => { - try { - const { ticketId } = req.body; - const agent = await Agent.findById(req.params.id); - const ticket = await Ticket.findById(ticketId); - - // Check if agent and ticket exist - if (!agent || !ticket) { - return res.status(404).json({ message: "Agent or Ticket not found" }); - } - - // Check if the ticket is assigned to this agent - if (!agent.assigned_tickets.includes(ticketId)) { - return res - .status(400) - .json({ message: "Ticket is not assigned to this agent" }); - } - - // Remove ticket from agent's assigned tickets - agent.assigned_tickets = agent.assigned_tickets.filter( - (id) => id.toString() !== ticketId - ); - await agent.save(); - - // Update ticket status to 'unassigned' - ticket.status = "unassigned"; - await ticket.save(); - - res - .status(200) - .json({ message: "Ticket unassigned from agent successfully", agent }); - } catch (err) { - res - .status(500) - .json({ message: "Error unassigning ticket from agent", error: err }); - } -}; - -// Change the status of an agent (active/inactive) -exports.changeAgentStatus = async (req, res) => { - try { - const { status } = req.body; - - // Ensure status is valid - if (!["active", "inactive"].includes(status)) { - return res - .status(400) - .json({ message: "Invalid status value, must be active or inactive" }); - } - - const agent = await Agent.findById(req.params.id); - - if (!agent) { - return res.status(404).json({ message: "Agent not found" }); - } - - agent.status = status; - await agent.save(); - - res - .status(200) - .json({ message: `Agent status updated to ${status}`, agent }); - } catch (err) { - res - .status(500) - .json({ message: "Error changing agent status", error: err }); - } -}; - -// Assign multiple tickets to an agent -exports.assignMultipleTickets = async (req, res) => { - try { - const { ticketIds } = req.body; // Expecting an array of ticket IDs - const agent = await Agent.findById(req.params.id); - - // Check if agent exists - if (!agent) { - return res.status(404).json({ message: "Agent not found" }); - } - - // Validate ticket IDs - const tickets = await Ticket.find({ _id: { $in: ticketIds } }); - - // Ensure all ticket IDs are valid - if (tickets.length !== ticketIds.length) { - return res.status(400).json({ message: "Some tickets were not found" }); - } - - // Check if any ticket is already assigned - const assignedTickets = tickets.filter( - (ticket) => ticket.status === "assigned" - ); - if (assignedTickets.length > 0) { - return res - .status(400) - .json({ message: "Some tickets are already assigned" }); - } - - // Assign tickets to agent - agent.assigned_tickets.push(...ticketIds); - await agent.save(); - - // Update ticket status to 'assigned' - for (let ticket of tickets) { - ticket.status = "assigned"; - await ticket.save(); - } - - res - .status(200) - .json({ - message: "Multiple tickets assigned to agent successfully", - agent, - }); - } catch (err) { - res - .status(500) - .json({ message: "Error assigning multiple tickets", error: err }); - } -}; - -// Handle Agent Role-based Access (admin vs support) -exports.checkAgentRole = async (req, res, next) => { - try { - const agent = await Agent.findById(req.params.id); - if (!agent) { - return res.status(404).json({ message: "Agent not found" }); - } - - if (agent.role !== "admin") { - return res - .status(403) - .json({ - message: "Permission denied, only admin can perform this action", - }); - } - - next(); - } catch (err) { - res.status(500).json({ message: "Error checking agent role", error: err }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/analyticcontroller.js b/backend/controllers/shop/sub-controllers/analyticcontroller.js deleted file mode 100644 index 805ee9cd..00000000 --- a/backend/controllers/shop/sub-controllers/analyticcontroller.js +++ /dev/null @@ -1,51 +0,0 @@ -const ProductAnalysis = require("../models/ProductAnalysis"); - -exports.createProductAnalysis = async (req, res) => { - try { - const { productId, views, sales, ratings, feedback } = req.body; - const productAnalysis = new ProductAnalysis({ - productId, - views, - sales, - ratings, - feedback, - }); - await productAnalysis.save(); - res.status(201).json(productAnalysis); - } catch (error) { - res - .status(400) - .json({ message: "Error creating product analysis data", error }); - } -}; - -exports.getProductAnalysis = async (req, res) => { - try { - const productAnalysis = await ProductAnalysis.findById(req.params.id); - if (!productAnalysis) - return res.status(404).json({ message: "Product analysis not found" }); - res.status(200).json(productAnalysis); - } catch (error) { - res - .status(400) - .json({ message: "Error retrieving product analysis", error }); - } -}; - -exports.updateProductAnalysis = async (req, res) => { - try { - const updatedData = req.body; - const productAnalysis = await ProductAnalysis.findByIdAndUpdate( - req.params.id, - updatedData, - { new: true } - ); - if (!productAnalysis) - return res.status(404).json({ message: "Product analysis not found" }); - res.status(200).json(productAnalysis); - } catch (error) { - res - .status(400) - .json({ message: "Error updating product analysis data", error }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/couponController.js b/backend/controllers/shop/sub-controllers/couponController.js deleted file mode 100644 index 1cead2f0..00000000 --- a/backend/controllers/shop/sub-controllers/couponController.js +++ /dev/null @@ -1,178 +0,0 @@ -const Coupon = require("../../../model/shop/sub-model/couponModel"); -const { validateCoupon } = require("../../../services/sub-service/couponValidator"); - -// Controller to Create a Coupon -exports.createCoupon = async (req, res) => { - try { - const coupon = new Coupon(req.body); - await coupon.save(); - res.status(201).json({ message: "Coupon created successfully", coupon }); - } catch (err) { - res.status(400).json({ error: err.message }); - } -}; - -// Controller to Get All Coupons -exports.getCoupons = async (req, res) => { - try { - const { status, minOrderAmount, startDate, endDate } = req.query; - const filters = {}; - - if (status) filters.status = status; - if (minOrderAmount) filters.minOrderAmount = { $gte: minOrderAmount }; - if (startDate || endDate) { - filters.startDate = { $gte: startDate || new Date() }; - filters.endDate = { $lte: endDate || new Date() }; - } - - const coupons = await Coupon.find(filters); - res.status(200).json(coupons); - } catch (err) { - res.status(400).json({ error: err.message }); - } -}; - -// Controller to Get Coupon by Code -exports.getCouponByCode = async (req, res) => { - try { - const coupon = await Coupon.findOne({ code: req.params.code }); - if (!coupon) { - return res.status(404).json({ error: "Coupon not found" }); - } - res.status(200).json(coupon); - } catch (err) { - res.status(400).json({ error: err.message }); - } -}; - -// Controller to Update Coupon -exports.updateCoupon = async (req, res) => { - try { - const updatedCoupon = await Coupon.findOneAndUpdate( - { code: req.params.code }, - { $set: req.body, updatedAt: Date.now() }, - { new: true } - ); - if (!updatedCoupon) { - return res.status(404).json({ error: "Coupon not found" }); - } - res.status(200).json(updatedCoupon); - } catch (err) { - res.status(400).json({ error: err.message }); - } -}; - -// Controller to Delete Coupon -exports.deleteCoupon = async (req, res) => { - try { - const deletedCoupon = await Coupon.findOneAndDelete({ - code: req.params.code, - }); - if (!deletedCoupon) { - return res.status(404).json({ error: "Coupon not found" }); - } - res.status(200).json({ message: "Coupon deleted successfully" }); - } catch (err) { - res.status(400).json({ error: err.message }); - } -}; - -// Controller to Validate Coupon -exports.validateCoupon = async (req, res, next) => { - const { code, orderAmount } = req.body; - try { - const coupon = await Coupon.findOne({ code }); - if (!coupon) return res.status(404).json({ error: "Coupon not found" }); - - // Validate coupon using helper function - const isValid = await validateCoupon(coupon, orderAmount); - if (!isValid) return res.status(400).json({ error: "Coupon is invalid" }); - - req.coupon = coupon; // Attach coupon to the request object for use in further steps - next(); - } catch (err) { - res.status(500).json({ error: "Error validating coupon" }); - } -}; - -// Controller to Track Coupon Usage (Increment Usage Count) -exports.incrementUsageCount = async (req, res) => { - try { - const { code } = req.body; - const coupon = await Coupon.findOne({ code }); - if (!coupon) return res.status(404).json({ error: "Coupon not found" }); - - // Increment the usage count by 1 - coupon.usageCount += 1; - - // Check if the usage limit has been reached - if (coupon.usageCount > coupon.usageLimit) { - return res.status(400).json({ error: "Coupon usage limit exceeded" }); - } - - await coupon.save(); - res.status(200).json({ message: "Coupon usage count incremented", coupon }); - } catch (err) { - res.status(400).json({ error: err.message }); - } -}; - -// Controller to Activate/Deactivate Coupon -exports.toggleCouponStatus = async (req, res) => { - try { - const { code } = req.params; - const { status } = req.body; // 'active' or 'inactive' - - if (!["active", "inactive"].includes(status)) { - return res.status(400).json({ error: "Invalid status value" }); - } - - const coupon = await Coupon.findOneAndUpdate( - { code }, - { status, updatedAt: Date.now() }, - { new: true } - ); - if (!coupon) { - return res.status(404).json({ error: "Coupon not found" }); - } - - res.status(200).json({ message: "Coupon status updated", coupon }); - } catch (err) { - res.status(400).json({ error: err.message }); - } -}; - -// Controller to Apply Coupon to an Order -exports.applyCouponToOrder = async (req, res) => { - const { code, orderAmount } = req.body; - try { - const coupon = await Coupon.findOne({ code }); - if (!coupon) return res.status(404).json({ error: "Coupon not found" }); - - const isValid = await validateCoupon(coupon, orderAmount); - if (!isValid) { - return res - .status(400) - .json({ error: "Coupon is invalid for this order" }); - } - - const discount = - coupon.discountType === "percentage" - ? (coupon.discountValue / 100) * orderAmount - : coupon.discountValue; - - // Apply max discount if it exists - const finalDiscount = coupon.maxDiscount - ? Math.min(discount, coupon.maxDiscount) - : discount; - - res - .status(200) - .json({ - message: "Coupon applied successfully", - discount: finalDiscount, - }); - } catch (err) { - res.status(400).json({ error: err.message }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/damagecontroller.js b/backend/controllers/shop/sub-controllers/damagecontroller.js deleted file mode 100644 index 6c95eb5d..00000000 --- a/backend/controllers/shop/sub-controllers/damagecontroller.js +++ /dev/null @@ -1,202 +0,0 @@ -const MalfunctioningProduct = require("../models/MalfunctioningProduct"); -const mongoose = require("mongoose"); - -// Create malfunctioning product -exports.createMalfunctioningProduct = async (req, res) => { - try { - const { productId, description, actionsTaken, createdBy } = req.body; - - // Validate if productId exists and is valid - if (!mongoose.Types.ObjectId.isValid(productId)) { - return res.status(400).json({ message: "Invalid product ID" }); - } - - // Check if the user exists - const userExists = await User.findById(createdBy); - if (!userExists) { - return res.status(404).json({ message: "User not found" }); - } - - const newProduct = new MalfunctioningProduct({ - productId, - description, - actionsTaken, - createdBy, - }); - - await newProduct.save(); - res.status(201).json(newProduct); - } catch (error) { - console.error(error); - res - .status(400) - .json({ - message: "Error creating malfunctioning product", - error: error.message, - }); - } -}; - -// Get malfunctioning product by ID -exports.getMalfunctioningProduct = async (req, res) => { - try { - const productId = req.params.id; - - // Validate if productId exists and is valid - if (!mongoose.Types.ObjectId.isValid(productId)) { - return res.status(400).json({ message: "Invalid product ID format" }); - } - - const product = await MalfunctioningProduct.findById(productId).populate( - "productId" - ); - - // Handle case where product is not found - if (!product) { - return res - .status(404) - .json({ message: "Malfunctioning product not found" }); - } - - res.status(200).json(product); - } catch (error) { - console.error(error); - res - .status(500) - .json({ - message: "Error retrieving malfunctioning product", - error: error.message, - }); - } -}; - -// Update malfunctioning product -exports.updateMalfunctioningProduct = async (req, res) => { - try { - const updatedData = req.body; - const productId = req.params.id; - - // Validate if productId exists and is valid - if (!mongoose.Types.ObjectId.isValid(productId)) { - return res.status(400).json({ message: "Invalid product ID format" }); - } - - // Check if any field is being updated and validate - if ( - !updatedData.productId && - !updatedData.description && - !updatedData.actionsTaken - ) { - return res.status(400).json({ message: "No valid fields to update" }); - } - - const product = await MalfunctioningProduct.findByIdAndUpdate( - productId, - updatedData, - { new: true } - ); - - // Handle case where product is not found - if (!product) { - return res.status(404).json({ message: "Product not found" }); - } - - res.status(200).json(product); - } catch (error) { - console.error(error); - res - .status(500) - .json({ - message: "Error updating malfunctioning product", - error: error.message, - }); - } -}; - -// Delete malfunctioning product -exports.deleteMalfunctioningProduct = async (req, res) => { - try { - const productId = req.params.id; - - // Validate if productId exists and is valid - if (!mongoose.Types.ObjectId.isValid(productId)) { - return res.status(400).json({ message: "Invalid product ID format" }); - } - - const product = await MalfunctioningProduct.findByIdAndDelete(productId); - - // Handle case where product is not found - if (!product) { - return res - .status(404) - .json({ message: "Malfunctioning product not found" }); - } - - res.status(200).json({ message: "Product deleted successfully" }); - } catch (error) { - console.error(error); - res - .status(500) - .json({ - message: "Error deleting malfunctioning product", - error: error.message, - }); - } -}; - -// Get all malfunctioning products with pagination and search -exports.getAllMalfunctioningProducts = async (req, res) => { - try { - const { page = 1, limit = 10, search = "" } = req.query; - const skip = (page - 1) * limit; - - const query = search - ? { description: { $regex: search, $options: "i" } } - : {}; - - const products = await MalfunctioningProduct.find(query) - .skip(skip) - .limit(parseInt(limit)) - .populate("productId") - .exec(); - - const totalCount = await MalfunctioningProduct.countDocuments(query); - - res.status(200).json({ - totalCount, - totalPages: Math.ceil(totalCount / limit), - currentPage: page, - products, - }); - } catch (error) { - console.error(error); - res - .status(500) - .json({ - message: "Error fetching malfunctioning products", - error: error.message, - }); - } -}; - -// Get count of malfunctioning products by status -exports.getMalfunctioningProductCountByStatus = async (req, res) => { - try { - const { status } = req.params; - - if (!["pending", "in progress", "resolved"].includes(status)) { - return res.status(400).json({ message: "Invalid status" }); - } - - const count = await MalfunctioningProduct.countDocuments({ status }); - res.status(200).json({ count }); - } catch (error) { - console.error(error); - res - .status(500) - .json({ - message: "Error fetching count by status", - error: error.message, - }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/deliveryPersonController.js b/backend/controllers/shop/sub-controllers/deliveryPersonController.js deleted file mode 100644 index ea24cc4b..00000000 --- a/backend/controllers/shop/sub-controllers/deliveryPersonController.js +++ /dev/null @@ -1,269 +0,0 @@ -const DeliveryPerson = require("../../../model/shop/sub-model/DeliveryPerson"); -const { hashPassword } = require("../../../services/sub-service/hashPassword"); -const { - validateEmail, - validatePhoneNumber, -} = require("../../../services/sub-service/couponValidator"); - -exports.successResponse = (res, statusCode, message, data = {}) => { - res.status(statusCode).json({ - status: "success", - message, - data, - }); -}; - -exports.errorResponse = (res, statusCode, message, error = {}) => { - res.status(statusCode).json({ - status: "error", - message, - error, - }); -}; - -// Create a new Delivery Person -exports.createDeliveryPerson = async (req, res) => { - try { - const { - name, - email, - phone_number, - status, - assigned_routes, - vehicle_details, - profile_picture, - password, - } = req.body; - - // Validate required fields - if (!name || !email || !phone_number || !status) { - return errorResponse(res, 400, "All required fields must be provided."); - } - - // Validate email and phone number formats - if (!validateEmail(email)) - return errorResponse(res, 400, "Invalid email format."); - if (!validatePhoneNumber(phone_number)) - return errorResponse(res, 400, "Invalid phone number format."); - - // Check if email already exists - const existingEmail = await DeliveryPerson.findOne({ email }); - if (existingEmail) return errorResponse(res, 400, "Email already exists."); - - // Hash password if provided - const hashedPassword = password ? await hashPassword(password) : undefined; - - const newDeliveryPerson = new DeliveryPerson({ - name, - email, - phone_number, - status, - assigned_routes, - vehicle_details, - profile_picture, - password: hashedPassword, - }); - - await newDeliveryPerson.save(); - successResponse( - res, - 201, - "Delivery person created successfully.", - newDeliveryPerson - ); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; - -// Get all Delivery Persons with pagination -exports.getAllDeliveryPersons = async (req, res) => { - try { - const { page = 1, limit = 10 } = req.query; - const deliveryPersons = await DeliveryPerson.find() - .select("name status vehicle_details.vehicle_type") - .limit(parseInt(limit)) - .skip((parseInt(page) - 1) * parseInt(limit)); - const count = await DeliveryPerson.countDocuments(); - - successResponse(res, 200, "Delivery persons retrieved successfully.", { - deliveryPersons, - totalPages: Math.ceil(count / limit), - currentPage: parseInt(page), - }); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; - -// Get a Delivery Person by ID -exports.getDeliveryPersonById = async (req, res) => { - try { - const deliveryPerson = await DeliveryPerson.findById( - req.params.id - ).populate("assigned_routes"); - if (!deliveryPerson) - return errorResponse(res, 404, "Delivery person not found."); - successResponse( - res, - 200, - "Delivery person retrieved successfully.", - deliveryPerson - ); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; - -// Update a Delivery Person -exports.updateDeliveryPerson = async (req, res) => { - try { - const updates = req.body; - - // Validate and hash password if provided - if (updates.password) - updates.password = await hashPassword(updates.password); - - // Validate email and phone number if updated - if (updates.email && !validateEmail(updates.email)) - return errorResponse(res, 400, "Invalid email format."); - if (updates.phone_number && !validatePhoneNumber(updates.phone_number)) - return errorResponse(res, 400, "Invalid phone number format."); - - // Check if email already exists (excluding current delivery person) - if (updates.email) { - const existingEmail = await DeliveryPerson.findOne({ - email: updates.email, - _id: { $ne: req.params.id }, - }); - if (existingEmail) - return errorResponse(res, 400, "Email already exists."); - } - - const updatedDeliveryPerson = await DeliveryPerson.findByIdAndUpdate( - req.params.id, - updates, - { new: true } - ); - if (!updatedDeliveryPerson) - return errorResponse(res, 404, "Delivery person not found."); - successResponse( - res, - 200, - "Delivery person updated successfully.", - updatedDeliveryPerson - ); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; - -// Soft delete (deactivate) a Delivery Person -exports.deleteDeliveryPerson = async (req, res) => { - try { - const deliveryPerson = await DeliveryPerson.findById(req.params.id); - if (!deliveryPerson) - return errorResponse(res, 404, "Delivery person not found."); - - deliveryPerson.status = "inactive"; - await deliveryPerson.save(); - successResponse(res, 200, "Delivery person deactivated successfully."); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; - -// Activate or Deactivate Delivery Person -exports.toggleStatus = async (req, res) => { - try { - const { status } = req.body; - if (!["active", "inactive"].includes(status)) - return errorResponse(res, 400, "Invalid status."); - - const deliveryPerson = await DeliveryPerson.findById(req.params.id); - if (!deliveryPerson) - return errorResponse(res, 404, "Delivery person not found."); - - deliveryPerson.status = status; - await deliveryPerson.save(); - successResponse(res, 200, "Delivery person status updated successfully.", { - status: deliveryPerson.status, - }); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; - -// Helper functions for response handling -const validateVehicleDetails = (vehicleDetails) => { - const { vehicle_type, vehicle_number } = vehicleDetails; - if (vehicle_type && typeof vehicle_type !== "string") return false; - if (vehicle_number && typeof vehicle_number !== "string") return false; - return true; -}; - -// Search Delivery Person by name -exports.searchDeliveryPersonByName = async (req, res) => { - try { - const { name } = req.query; - const deliveryPersons = await DeliveryPerson.find({ - name: { $regex: name, $options: "i" }, - }); - successResponse( - res, - 200, - "Search results retrieved successfully.", - deliveryPersons - ); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; - -// Get all assigned routes for a Delivery Person -exports.getAssignedRoutes = async (req, res) => { - try { - const deliveryPerson = await DeliveryPerson.findById( - req.params.id - ).populate("assigned_routes"); - if (!deliveryPerson) - return errorResponse(res, 404, "Delivery person not found."); - successResponse( - res, - 200, - "Assigned routes retrieved successfully.", - deliveryPerson.assigned_routes - ); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; - -// Change Delivery Person's vehicle details -exports.updateVehicleDetails = async (req, res) => { - try { - const { vehicle_details } = req.body; - - // Validate vehicle details format - if (vehicle_details && !validateVehicleDetails(vehicle_details)) { - return errorResponse(res, 400, "Invalid vehicle details format."); - } - - const updatedDeliveryPerson = await DeliveryPerson.findByIdAndUpdate( - req.params.id, - { vehicle_details }, - { new: true } - ); - - if (!updatedDeliveryPerson) - return errorResponse(res, 404, "Delivery person not found."); - successResponse( - res, - 200, - "Vehicle details updated successfully.", - updatedDeliveryPerson.vehicle_details - ); - } catch (error) { - errorResponse(res, 500, error.message); - } -}; diff --git a/backend/controllers/shop/sub-controllers/giftCardController.js b/backend/controllers/shop/sub-controllers/giftCardController.js deleted file mode 100644 index da430178..00000000 --- a/backend/controllers/shop/sub-controllers/giftCardController.js +++ /dev/null @@ -1,311 +0,0 @@ -// controllers/giftCardController.js -const GiftCard = require("../../../model/shop/sub-model/GiftCard"); - -// Create a new gift card -exports.createGiftCard = async (req, res) => { - try { - const { value, userId, expiryDate } = req.body; - - if (value <= 0) { - return res - .status(400) - .json({ message: "Gift card value must be greater than 0" }); - } - - const cardNumber = generateCardNumber(); - - const newGiftCard = new GiftCard({ - cardNumber, - value, - userId, - expiryDate, - }); - - await newGiftCard.save(); - res - .status(201) - .json({ - message: "Gift card created successfully", - giftCard: newGiftCard, - }); - } catch (err) { - res - .status(500) - .json({ message: "Error creating gift card", error: err.message }); - } -}; - -// Redeem a gift card -exports.redeemGiftCard = async (req, res) => { - try { - const { cardNumber } = req.body; - - const giftCard = await GiftCard.findOne({ cardNumber }); - - if (!giftCard) { - return res.status(404).json({ message: "Gift card not found" }); - } - - if (giftCard.status === "redeemed") { - return res.status(400).json({ message: "Gift card already redeemed" }); - } - - if (giftCard.status === "expired") { - return res.status(400).json({ message: "Gift card is expired" }); - } - - if (giftCard.expiryDate < new Date()) { - giftCard.status = "expired"; - await giftCard.save(); - return res.status(400).json({ message: "Gift card has expired" }); - } - - if (giftCard.value <= 0) { - return res.status(400).json({ message: "Gift card value is invalid" }); - } - - giftCard.status = "redeemed"; - await giftCard.save(); - - res - .status(200) - .json({ message: "Gift card redeemed successfully", giftCard }); - } catch (err) { - res - .status(500) - .json({ message: "Error redeeming gift card", error: err.message }); - } -}; - -// Fetch gift card details -exports.getGiftCardDetails = async (req, res) => { - try { - const { cardNumber } = req.params; - const giftCard = await GiftCard.findOne({ cardNumber }); - - if (!giftCard) { - return res.status(404).json({ message: "Gift card not found" }); - } - - res.status(200).json({ giftCard }); - } catch (err) { - res - .status(500) - .json({ - message: "Error fetching gift card details", - error: err.message, - }); - } -}; - -// Fetch all active gift cards for a user -exports.getUserGiftCards = async (req, res) => { - try { - const { userId } = req.params; - - const giftCards = await GiftCard.find({ userId, status: "active" }); - - if (giftCards.length === 0) { - return res - .status(404) - .json({ message: "No active gift cards found for this user" }); - } - - res.status(200).json({ giftCards }); - } catch (err) { - res - .status(500) - .json({ message: "Error fetching user gift cards", error: err.message }); - } -}; - -// Extend gift card expiration -exports.extendGiftCardExpiry = async (req, res) => { - try { - const { cardNumber, newExpiryDate } = req.body; - - const giftCard = await GiftCard.findOne({ cardNumber }); - - if (!giftCard) { - return res.status(404).json({ message: "Gift card not found" }); - } - - if (giftCard.status === "redeemed") { - return res - .status(400) - .json({ message: "Cannot extend expiry of redeemed card" }); - } - - if (giftCard.status === "expired") { - return res - .status(400) - .json({ message: "Cannot extend expiry of expired card" }); - } - - giftCard.expiryDate = new Date(newExpiryDate); - await giftCard.save(); - - res - .status(200) - .json({ message: "Gift card expiry extended successfully", giftCard }); - } catch (err) { - res - .status(500) - .json({ - message: "Error extending gift card expiry", - error: err.message, - }); - } -}; - -// Deactivate a gift card -exports.deactivateGiftCard = async (req, res) => { - try { - const { cardNumber } = req.body; - - const giftCard = await GiftCard.findOne({ cardNumber }); - - if (!giftCard) { - return res.status(404).json({ message: "Gift card not found" }); - } - - if (giftCard.status === "redeemed") { - return res - .status(400) - .json({ message: "Cannot deactivate redeemed card" }); - } - - giftCard.status = "expired"; - await giftCard.save(); - - res - .status(200) - .json({ message: "Gift card deactivated successfully", giftCard }); - } catch (err) { - res - .status(500) - .json({ message: "Error deactivating gift card", error: err.message }); - } -}; - -// Delete a gift card (force delete) -exports.deleteGiftCard = async (req, res) => { - try { - const { cardNumber } = req.body; - - const giftCard = await GiftCard.findOne({ cardNumber }); - - if (!giftCard) { - return res.status(404).json({ message: "Gift card not found" }); - } - - await giftCard.remove(); - res.status(200).json({ message: "Gift card deleted successfully" }); - } catch (err) { - res - .status(500) - .json({ message: "Error deleting gift card", error: err.message }); - } -}; - -// Reactivate an expired gift card -exports.reactivateGiftCard = async (req, res) => { - try { - const { cardNumber } = req.body; - - const giftCard = await GiftCard.findOne({ cardNumber }); - - if (!giftCard) { - return res.status(404).json({ message: "Gift card not found" }); - } - - if (giftCard.status === "redeemed") { - return res - .status(400) - .json({ message: "Cannot reactivate redeemed card" }); - } - - if (giftCard.status === "active") { - return res.status(400).json({ message: "Gift card is already active" }); - } - - giftCard.status = "active"; - giftCard.expiryDate = new Date(); // Reset the expiry date to a new default - await giftCard.save(); - - res - .status(200) - .json({ message: "Gift card reactivated successfully", giftCard }); - } catch (err) { - res - .status(500) - .json({ message: "Error reactivating gift card", error: err.message }); - } -}; - -// Update the value of a gift card -exports.updateGiftCardValue = async (req, res) => { - try { - const { cardNumber, newValue } = req.body; - - if (newValue <= 0) { - return res - .status(400) - .json({ message: "New value must be greater than 0" }); - } - - const giftCard = await GiftCard.findOne({ cardNumber }); - - if (!giftCard) { - return res.status(404).json({ message: "Gift card not found" }); - } - - giftCard.value = newValue; - await giftCard.save(); - - res - .status(200) - .json({ message: "Gift card value updated successfully", giftCard }); - } catch (err) { - res - .status(500) - .json({ message: "Error updating gift card value", error: err.message }); - } -}; - -// Search for gift cards by value range -exports.searchGiftCardsByValue = async (req, res) => { - try { - const { minValue, maxValue } = req.query; - - if (minValue <= 0 || maxValue <= 0) { - return res - .status(400) - .json({ message: "Value range must be greater than 0" }); - } - - const giftCards = await GiftCard.find({ - value: { $gte: minValue, $lte: maxValue }, - }); - - if (giftCards.length === 0) { - return res - .status(404) - .json({ message: "No gift cards found within this value range" }); - } - - res.status(200).json({ giftCards }); - } catch (err) { - res - .status(500) - .json({ - message: "Error searching gift cards by value", - error: err.message, - }); - } -}; - -// Helper function to generate a unique card number -const generateCardNumber = () => { - return `GC-${Math.random().toString(36).substr(2, 9).toUpperCase()}`; -}; diff --git a/backend/controllers/shop/sub-controllers/inventoryController.js b/backend/controllers/shop/sub-controllers/inventoryController.js deleted file mode 100644 index 21b3148d..00000000 --- a/backend/controllers/shop/sub-controllers/inventoryController.js +++ /dev/null @@ -1,343 +0,0 @@ -const Inventory = require("../../../model/shop/sub-model/InventoryModel"); -const Product = require("../../../model/shop/product"); -const Supplier = require("../../../model/shop/sub-model/SuppierModel"); -const mongoose = require("mongoose"); - - -exports.createInventoryItem = async (req, res) => { - try { - const { - productId, - currentStockLevel, - reorderLevel, - warehouseLocation, - supplierId, - performedBy, - } = req.body; - - // Ensure product exists - const product = await Product.findById(productId); - if (!product) { - return res.status(400).json({ message: "Product not found" }); - } - - // Optional: Check if supplier exists (if provided) - if (supplierId) { - const supplier = await Supplier.findById(supplierId); - if (!supplier) { - return res.status(400).json({ message: "Supplier not found" }); - } - } - - const newInventoryItem = new Inventory({ - productId, - currentStockLevel, - reorderLevel, - warehouseLocation, - supplierId, - }); - - // Adding audit log for creation - newInventoryItem.auditLog.push({ - action: "Inventory Item Created", - performedBy, - quantityChanged: currentStockLevel, - notes: `Initial stock for ${product.name}`, - }); - - await newInventoryItem.save(); - res - .status(201) - .json({ - message: "Inventory item created successfully", - newInventoryItem, - }); - } catch (error) { - res.status(500).json({ message: "Error creating inventory item", error }); - } -}; - -// Controller for updating stock level -exports.updateStockLevel = async (req, res) => { - try { - const { inventoryId, newStockLevel, performedBy, notes } = req.body; - - if (newStockLevel < 0) { - return res - .status(400) - .json({ message: "Stock level cannot be negative" }); - } - - const inventory = await Inventory.findById(inventoryId); - if (!inventory) { - return res.status(404).json({ message: "Inventory item not found" }); - } - - const quantityChanged = newStockLevel - inventory.currentStockLevel; - inventory.currentStockLevel = newStockLevel; - inventory.auditLog.push({ - action: "Stock Level Updated", - performedBy, - quantityChanged, - notes, - }); - - await inventory.save(); - res - .status(200) - .json({ message: "Stock level updated successfully", inventory }); - } catch (error) { - res.status(500).json({ message: "Error updating stock level", error }); - } -}; - -// Controller to fetch inventory by product -exports.fetchInventoryByProduct = async (req, res) => { - try { - const { productId } = req.params; - const inventoryItem = await Inventory.findOne({ productId }) - .populate("productId") - .populate("supplierId"); - - if (!inventoryItem) { - return res - .status(404) - .json({ message: "Inventory not found for this product" }); - } - - res.status(200).json({ inventoryItem }); - } catch (error) { - res - .status(500) - .json({ message: "Error fetching inventory by product", error }); - } -}; - -// Controller to fetch inventory by warehouse -exports.fetchInventoryByWarehouse = async (req, res) => { - try { - const { warehouseLocation } = req.params; - const inventoryItems = await Inventory.find({ warehouseLocation }) - .populate("productId") - .populate("supplierId"); - - if (!inventoryItems || inventoryItems.length === 0) { - return res - .status(404) - .json({ message: "No inventory found for this warehouse" }); - } - - res.status(200).json({ inventoryItems }); - } catch (error) { - res - .status(500) - .json({ message: "Error fetching inventory by warehouse", error }); - } -}; - -// Controller to fetch all inventory -exports.fetchAllInventory = async (req, res) => { - try { - const inventoryItems = await Inventory.find() - .populate("productId") - .populate("supplierId"); - - if (!inventoryItems || inventoryItems.length === 0) { - return res.status(404).json({ message: "No inventory items found" }); - } - - res.status(200).json({ inventoryItems }); - } catch (error) { - res.status(500).json({ message: "Error fetching all inventory", error }); - } -}; - -// Controller to delete an inventory item -exports.deleteInventoryItem = async (req, res) => { - try { - const { inventoryId } = req.params; - const inventory = await Inventory.findById(inventoryId); - - if (!inventory) { - return res.status(404).json({ message: "Inventory item not found" }); - } - - await inventory.remove(); - res.status(200).json({ message: "Inventory item deleted successfully" }); - } catch (error) { - res.status(500).json({ message: "Error deleting inventory item", error }); - } -}; - -// Controller for bulk updating stock levels -exports.bulkUpdateStockLevels = async (req, res) => { - try { - const { updates, performedBy } = req.body; - - const updatedItems = []; - for (const update of updates) { - const { inventoryId, newStockLevel, notes } = update; - const inventory = await Inventory.findById(inventoryId); - - if (!inventory) { - return res - .status(404) - .json({ message: `Inventory item with ID ${inventoryId} not found` }); - } - - const quantityChanged = newStockLevel - inventory.currentStockLevel; - inventory.currentStockLevel = newStockLevel; - inventory.auditLog.push({ - action: "Stock Level Updated (Bulk)", - performedBy, - quantityChanged, - notes, - }); - - await inventory.save(); - updatedItems.push(inventory); - } - - res - .status(200) - .json({ - message: "Bulk stock levels updated successfully", - updatedItems, - }); - } catch (error) { - res - .status(500) - .json({ message: "Error updating stock levels in bulk", error }); - } -}; - -// Controller for bulk creation of inventory items -exports.bulkCreateInventoryItems = async (req, res) => { - try { - const { items, performedBy } = req.body; - const createdItems = []; - - for (const item of items) { - const { - productId, - currentStockLevel, - reorderLevel, - warehouseLocation, - supplierId, - } = item; - - // Ensure product exists - const product = await Product.findById(productId); - if (!product) { - return res - .status(400) - .json({ message: `Product with ID ${productId} not found` }); - } - - // Optional: Check if supplier exists (if provided) - if (supplierId) { - const supplier = await Supplier.findById(supplierId); - if (!supplier) { - return res - .status(400) - .json({ message: `Supplier with ID ${supplierId} not found` }); - } - } - - const newInventoryItem = new Inventory({ - productId, - currentStockLevel, - reorderLevel, - warehouseLocation, - supplierId, - }); - - newInventoryItem.auditLog.push({ - action: "Inventory Item Created (Bulk)", - performedBy, - quantityChanged: currentStockLevel, - notes: `Initial stock for ${product.name}`, - }); - - await newInventoryItem.save(); - createdItems.push(newInventoryItem); - } - - res - .status(201) - .json({ - message: "Bulk inventory items created successfully", - createdItems, - }); - } catch (error) { - res - .status(500) - .json({ message: "Error creating inventory items in bulk", error }); - } -}; - -// Controller for logging actions in inventory audit trail -exports.logInventoryAction = async (req, res) => { - try { - const { inventoryId, action, performedBy, quantityChanged, notes } = - req.body; - - const inventory = await Inventory.findById(inventoryId); - if (!inventory) { - return res.status(404).json({ message: "Inventory item not found" }); - } - - inventory.auditLog.push({ - action, - performedBy, - quantityChanged, - notes, - }); - - await inventory.save(); - res.status(200).json({ message: "Action logged successfully" }); - } catch (error) { - res.status(500).json({ message: "Error logging action", error }); - } -}; - -// Controller for handling expired inventory (e.g., perishable items) -exports.handleExpiredInventory = async (req, res) => { - try { - const { productId } = req.params; - const expiredInventory = await Inventory.find({ - productId, - currentStockLevel: { $gt: 0 }, - lastRestockedDate: { $lt: new Date() }, - }); - - if (expiredInventory.length === 0) { - return res - .status(404) - .json({ message: "No expired inventory found for this product" }); - } - - for (const inventory of expiredInventory) { - inventory.currentStockLevel = 0; // Mark stock as zero - inventory.auditLog.push({ - action: "Expired Inventory Removed", - performedBy: "System", - quantityChanged: -inventory.currentStockLevel, - notes: "Inventory marked as expired", - }); - - await inventory.save(); - } - - res - .status(200) - .json({ - message: "Expired inventory handled successfully", - expiredInventory, - }); - } catch (error) { - res - .status(500) - .json({ message: "Error handling expired inventory", error }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/invoiceController.js b/backend/controllers/shop/sub-controllers/invoiceController.js deleted file mode 100644 index 41cc8388..00000000 --- a/backend/controllers/shop/sub-controllers/invoiceController.js +++ /dev/null @@ -1,217 +0,0 @@ -const Invoice = require("../models/invoice"); -const Joi = require("joi"); - -// Validation Schemas -const invoiceSchema = Joi.object({ - orderId: Joi.string().required(), - userId: Joi.string().required(), - amount: Joi.number().min(0).required(), - dueDate: Joi.date().required(), - paymentId: Joi.string().optional(), -}); - -const statusUpdateSchema = Joi.object({ - status: Joi.string() - .valid("Paid", "Unpaid", "Overdue", "Cancelled") - .required(), -}); - -// Generate invoice after payment confirmation -const generateInvoice = async (req, res) => { - const { error, value } = invoiceSchema.validate(req.body); - if (error) return res.status(400).json({ message: error.message }); - - const { orderId, userId, amount, dueDate, paymentId } = value; - - const newInvoice = new Invoice({ - invoiceId: `INV${Date.now()}`, - orderId, - userId, - amount, - dueDate, - paymentId, - }); - - try { - const invoice = await newInvoice.save(); - res.status(201).json(invoice); - } catch (error) { - console.error(`Error generating invoice: ${error.message}`); - res.status(500).json({ message: "Internal server error" }); - } -}; - -// Retrieve invoices by user, order, status, or date range with pagination -const getInvoices = async (req, res) => { - const { - userId, - orderId, - status, - startDate, - endDate, - page = 1, - limit = 10, - sortBy = "invoiceDate", - order = "desc", - } = req.query; - - try { - const filters = {}; - if (userId) filters.userId = userId; - if (orderId) filters.orderId = orderId; - if (status) filters.status = status; - - if (startDate || endDate) { - filters.invoiceDate = {}; - if (startDate) filters.invoiceDate.$gte = new Date(startDate); - if (endDate) filters.invoiceDate.$lte = new Date(endDate); - } - - const invoices = await Invoice.find(filters) - .sort({ [sortBy]: order === "asc" ? 1 : -1 }) - .skip((page - 1) * limit) - .limit(Number(limit)); - - res.status(200).json(invoices); - } catch (error) { - console.error(`Error fetching invoices: ${error.message}`); - res.status(500).json({ message: "Internal server error" }); - } -}; - -// Retrieve a single invoice by ID -const getInvoiceById = async (req, res) => { - try { - const invoice = await Invoice.findById(req.params.id); - if (!invoice) return res.status(404).json({ message: "Invoice not found" }); - res.status(200).json(invoice); - } catch (error) { - console.error(`Error fetching invoice by ID: ${error.message}`); - res.status(500).json({ message: "Internal server error" }); - } -}; - -// Update invoice status with validation -const updateInvoiceStatus = async (req, res) => { - const { error, value } = statusUpdateSchema.validate(req.body); - if (error) return res.status(400).json({ message: error.message }); - - try { - const invoice = await Invoice.findByIdAndUpdate( - req.params.id, - { status: value.status }, - { new: true } - ); - if (!invoice) return res.status(404).json({ message: "Invoice not found" }); - res.status(200).json(invoice); - } catch (error) { - console.error(`Error updating invoice status: ${error.message}`); - res.status(500).json({ message: "Internal server error" }); - } -}; - -// Delete an invoice by ID -const deleteInvoice = async (req, res) => { - try { - const invoice = await Invoice.findByIdAndDelete(req.params.id); - if (!invoice) return res.status(404).json({ message: "Invoice not found" }); - res.status(200).json({ message: "Invoice deleted successfully" }); - } catch (error) { - console.error(`Error deleting invoice: ${error.message}`); - res.status(500).json({ message: "Internal server error" }); - } -}; - -// Mark overdue invoices -const markOverdueInvoices = async (req, res) => { - try { - const overdueInvoices = await Invoice.updateMany( - { dueDate: { $lt: new Date() }, status: "Unpaid" }, - { status: "Overdue" } - ); - res - .status(200) - .json({ - message: `${overdueInvoices.nModified} invoices marked as overdue`, - }); - } catch (error) { - console.error(`Error marking overdue invoices: ${error.message}`); - res.status(500).json({ message: "Internal server error" }); - } -}; - -// Summary of invoices by status -const invoiceSummary = async (req, res) => { - const { userId } = req.query; - - try { - const match = userId ? { userId } : {}; - - const summary = await Invoice.aggregate([ - { $match: match }, - { - $group: { - _id: "$status", - totalAmount: { $sum: "$amount" }, - count: { $sum: 1 }, - }, - }, - ]); - - const summaryData = summary.reduce((acc, item) => { - acc[item._id] = { totalAmount: item.totalAmount, count: item.count }; - return acc; - }, {}); - - res.status(200).json(summaryData); - } catch (error) { - console.error(`Error generating invoice summary: ${error.message}`); - res.status(500).json({ message: "Internal server error" }); - } -}; - -// Bulk invoice generation -const generateBulkInvoices = async (req, res) => { - const { invoices } = req.body; - - if (!Array.isArray(invoices) || invoices.length === 0) { - return res.status(400).json({ message: "Invalid invoices data" }); - } - - const validationErrors = invoices - .map((invoiceData, index) => { - const { error } = invoiceSchema.validate(invoiceData); - return error ? { index, message: error.message } : null; - }) - .filter(Boolean); - - if (validationErrors.length > 0) { - return res - .status(400) - .json({ message: "Validation errors", errors: validationErrors }); - } - - try { - const invoiceDocuments = invoices.map((invoiceData) => ({ - ...invoiceData, - invoiceId: `INV${Date.now() + Math.floor(Math.random() * 1000)}`, - })); - - const createdInvoices = await Invoice.insertMany(invoiceDocuments); - res.status(201).json(createdInvoices); - } catch (error) { - console.error(`Error generating bulk invoices: ${error.message}`); - res.status(500).json({ message: "Internal server error" }); - } -}; - -module.exports = { - generateInvoice, - getInvoices, - getInvoiceById, - updateInvoiceStatus, - deleteInvoice, - markOverdueInvoices, - invoiceSummary, - generateBulkInvoices, -}; diff --git a/backend/controllers/shop/sub-controllers/loyaltyPointsController.js b/backend/controllers/shop/sub-controllers/loyaltyPointsController.js deleted file mode 100644 index f2c6c5a7..00000000 --- a/backend/controllers/shop/sub-controllers/loyaltyPointsController.js +++ /dev/null @@ -1,264 +0,0 @@ -const LoyaltyPoint = require("../../../model/shop/sub-model/loyaltyPointModel"); -const User = require("../../../model/user"); - -// Award points to a user -exports.awardPoints = async (req, res) => { - try { - const { userId, points, earnedBy } = req.body; - - const user = await User.findById(userId); - if (!user) return res.status(404).json({ message: "User not found" }); - - const newPoints = new LoyaltyPoint({ userId, points, earnedBy }); - await newPoints.save(); - - user.loyaltyPoints += points; - await user.save(); - - res - .status(200) - .json({ message: "Points awarded successfully", points: newPoints }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Get a user's loyalty points balance -exports.getPoints = async (req, res) => { - try { - const { userId } = req.params; - - const points = await LoyaltyPoint.aggregate([ - { $match: { userId: mongoose.Types.ObjectId(userId) } }, - { $group: { _id: "$userId", totalPoints: { $sum: "$points" } } }, - ]); - - if (!points.length) - return res.status(404).json({ message: "No points found for this user" }); - - res.status(200).json({ totalPoints: points[0].totalPoints }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Get transaction history of loyalty points -exports.getTransactionHistory = async (req, res) => { - try { - const { userId } = req.params; - - const transactions = await LoyaltyPoint.find({ userId }).sort({ - timestamp: -1, - }); - - if (!transactions.length) - return res - .status(404) - .json({ message: "No transaction history found for this user" }); - - res.status(200).json({ transactions }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Delete a specific loyalty point entry -exports.deletePoints = async (req, res) => { - try { - const { transactionId } = req.params; - - const deletedTransaction = await LoyaltyPoint.findByIdAndDelete( - transactionId - ); - if (!deletedTransaction) - return res.status(404).json({ message: "Transaction not found" }); - - res - .status(200) - .json({ - message: "Loyalty points transaction deleted", - transaction: deletedTransaction, - }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Update a specific loyalty point transaction -exports.updatePoints = async (req, res) => { - try { - const { transactionId } = req.params; - const { points, earnedBy } = req.body; - - const updatedTransaction = await LoyaltyPoint.findByIdAndUpdate( - transactionId, - { points, earnedBy }, - { new: true } - ); - - if (!updatedTransaction) - return res.status(404).json({ message: "Transaction not found" }); - - res - .status(200) - .json({ - message: "Loyalty points transaction updated", - transaction: updatedTransaction, - }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Filter transactions by earning type (e.g., 'purchase', 'referral') -exports.filterTransactionsByType = async (req, res) => { - try { - const { userId } = req.params; - const { type } = req.query; - - const transactions = await LoyaltyPoint.find({ userId, earnedBy: type }); - - if (!transactions.length) - return res - .status(404) - .json({ message: `No transactions found for ${type}` }); - - res.status(200).json({ transactions }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Get total points earned by referral actions -exports.getPointsByReferrals = async (req, res) => { - try { - const { userId } = req.params; - - const referralPoints = await LoyaltyPoint.aggregate([ - { - $match: { - userId: mongoose.Types.ObjectId(userId), - earnedBy: "referral", - }, - }, - { $group: { _id: "$userId", totalReferralPoints: { $sum: "$points" } } }, - ]); - - if (!referralPoints.length) - return res - .status(404) - .json({ message: "No referral points found for this user" }); - - res - .status(200) - .json({ totalReferralPoints: referralPoints[0].totalReferralPoints }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Get total points earned by purchase actions -exports.getPointsByPurchases = async (req, res) => { - try { - const { userId } = req.params; - - const purchasePoints = await LoyaltyPoint.aggregate([ - { - $match: { - userId: mongoose.Types.ObjectId(userId), - earnedBy: "purchase", - }, - }, - { $group: { _id: "$userId", totalPurchasePoints: { $sum: "$points" } } }, - ]); - - if (!purchasePoints.length) - return res - .status(404) - .json({ message: "No purchase points found for this user" }); - - res - .status(200) - .json({ totalPurchasePoints: purchasePoints[0].totalPurchasePoints }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Redeem points (reduce points based on redemption) -exports.redeemPoints = async (req, res) => { - try { - const { userId, pointsToRedeem } = req.body; - - const user = await User.findById(userId); - if (!user) return res.status(404).json({ message: "User not found" }); - - const totalPoints = await LoyaltyPoint.aggregate([ - { $match: { userId: mongoose.Types.ObjectId(userId) } }, - { $group: { _id: "$userId", totalPoints: { $sum: "$points" } } }, - ]); - - if (totalPoints[0].totalPoints < pointsToRedeem) { - return res - .status(400) - .json({ message: "Insufficient points for redemption" }); - } - - const redemption = new LoyaltyPoint({ - userId, - points: -pointsToRedeem, - earnedBy: "redemption", - }); - await redemption.save(); - - res - .status(200) - .json({ message: "Points redeemed successfully", redemption }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; - -// Calculate loyalty point summary (overall breakdown) -exports.getLoyaltySummary = async (req, res) => { - try { - const { userId } = req.params; - - const totalPoints = await LoyaltyPoint.aggregate([ - { $match: { userId: mongoose.Types.ObjectId(userId) } }, - { $group: { _id: "$userId", totalPoints: { $sum: "$points" } } }, - ]); - - const referralPoints = await LoyaltyPoint.aggregate([ - { - $match: { - userId: mongoose.Types.ObjectId(userId), - earnedBy: "referral", - }, - }, - { $group: { _id: "$userId", totalReferralPoints: { $sum: "$points" } } }, - ]); - - const purchasePoints = await LoyaltyPoint.aggregate([ - { - $match: { - userId: mongoose.Types.ObjectId(userId), - earnedBy: "purchase", - }, - }, - { $group: { _id: "$userId", totalPurchasePoints: { $sum: "$points" } } }, - ]); - - res.status(200).json({ - totalPoints: totalPoints.length ? totalPoints[0].totalPoints : 0, - referralPoints: referralPoints.length - ? referralPoints[0].totalReferralPoints - : 0, - purchasePoints: purchasePoints.length - ? purchasePoints[0].totalPurchasePoints - : 0, - }); - } catch (error) { - res.status(500).json({ message: "Server error", error }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/orderController.js b/backend/controllers/shop/sub-controllers/orderController.js deleted file mode 100644 index 503e9180..00000000 --- a/backend/controllers/shop/sub-controllers/orderController.js +++ /dev/null @@ -1,297 +0,0 @@ -const OrderHistory = require("../../../model/shop/sub-model/OrderHistory"); -const Product = require("../../../model/shop/product"); -const User = require("../../../model/user"); - - -exports.createOrder = async (req, res) => { - try { - const { userId, items, shippingAddress, paymentDetails } = req.body; - - // Validate user - const user = await User.findById(userId); - if (!user) return res.status(400).json({ message: "User not found" }); - - // Validate product availability and calculate total amount - let totalAmount = 0; - for (const item of items) { - const product = await Product.findById(item.productId); - if (!product) - return res - .status(400) - .json({ message: `Product with ID ${item.productId} not found` }); - totalAmount += product.price * item.quantity; - } - - const order = new OrderHistory({ - userId, - items, - shippingAddress, - totalAmount, - paymentStatus: paymentDetails.status || "Pending", - }); - - await order.save(); - res.status(201).json({ message: "Order created successfully", order }); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.getOrders = async (req, res) => { - try { - const userId = req.user.id; // Assume authentication middleware sets req.user - - const orders = await OrderHistory.find({ userId }) - .populate("items.productId") - .select("orderId orderDate orderStatus totalAmount items shippingAddress") - .exec(); - - if (!orders) return res.status(404).json({ message: "No orders found" }); - res.status(200).json(orders); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.updateOrderStatus = async (req, res) => { - try { - const { orderId } = req.params; - const { orderStatus, trackingNumber } = req.body; - const userId = req.user.id; // Assume authentication middleware - - // Fetch the order - const order = await OrderHistory.findById(orderId); - if (!order) return res.status(404).json({ message: "Order not found" }); - - // Ensure that the user is allowed to update the order - if (order.userId.toString() !== userId && !req.user.isAdmin) { - return res.status(403).json({ message: "Unauthorized" }); - } - - // Update order status and tracking number if provided - order.orderStatus = orderStatus; - if (trackingNumber) { - order.trackingNumber = trackingNumber; - } - - await order.save(); - res - .status(200) - .json({ message: "Order status updated successfully", order }); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.deleteOrder = async (req, res) => { - try { - const { orderId } = req.params; - const userId = req.user.id; // Assume authentication middleware - - // Fetch the order - const order = await OrderHistory.findById(orderId); - if (!order) return res.status(404).json({ message: "Order not found" }); - - // Ensure that the user is allowed to delete the order - if (order.userId.toString() !== userId && !req.user.isAdmin) { - return res.status(403).json({ message: "Unauthorized" }); - } - - // Check order status (e.g., only allow deletion if "Pending") - if (order.orderStatus !== "Pending") { - return res - .status(400) - .json({ message: "Cannot delete non-pending orders" }); - } - - await order.remove(); - res.status(200).json({ message: "Order deleted successfully" }); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.getOrderById = async (req, res) => { - try { - const { orderId } = req.params; - const userId = req.user.id; // Assume authentication middleware sets req.user - - const order = await OrderHistory.findOne({ _id: orderId, userId }) - .populate("items.productId", "name price") - .exec(); - - if (!order) return res.status(404).json({ message: "Order not found" }); - - res.status(200).json(order); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.addItemToOrder = async (req, res) => { - try { - const { orderId } = req.params; - const { productId, quantity } = req.body; - - const order = await OrderHistory.findById(orderId); - if (!order) return res.status(404).json({ message: "Order not found" }); - - const product = await Product.findById(productId); - if (!product) return res.status(400).json({ message: "Product not found" }); - if (product.stock < quantity) - return res.status(400).json({ message: "Insufficient stock" }); - - // Add item to order - const item = { productId, quantity, price: product.price }; - order.items.push(item); - order.totalAmount += product.price * quantity; - - await order.save(); - res.status(200).json({ message: "Item added to order", order }); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.removeItemFromOrder = async (req, res) => { - try { - const { orderId, itemId } = req.params; - - const order = await OrderHistory.findById(orderId); - if (!order) return res.status(404).json({ message: "Order not found" }); - - const itemIndex = order.items.findIndex( - (item) => item._id.toString() === itemId - ); - if (itemIndex === -1) - return res.status(404).json({ message: "Item not found in order" }); - - const item = order.items[itemIndex]; - order.totalAmount -= item.price * item.quantity; - order.items.splice(itemIndex, 1); // Remove item from array - - await order.save(); - res.status(200).json({ message: "Item removed from order", order }); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.updateOrderItemQuantity = async (req, res) => { - try { - const { orderId, itemId } = req.params; - const { quantity } = req.body; - - const order = await OrderHistory.findById(orderId); - if (!order) return res.status(404).json({ message: "Order not found" }); - - const item = order.items.find((item) => item._id.toString() === itemId); - if (!item) - return res.status(404).json({ message: "Item not found in order" }); - - const product = await Product.findById(item.productId); - if (product.stock < quantity) - return res.status(400).json({ message: "Insufficient stock" }); - - // Update totalAmount by adjusting only the quantity difference - order.totalAmount += (quantity - item.quantity) * item.price; - item.quantity = quantity; - - await order.save(); - res.status(200).json({ message: "Order item quantity updated", order }); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.bulkUpdateOrderStatus = async (req, res) => { - try { - const { orderIds, orderStatus } = req.body; - - const updatedOrders = await OrderHistory.updateMany( - { _id: { $in: orderIds } }, - { $set: { orderStatus } } - ); - - res - .status(200) - .json({ message: "Order statuses updated successfully", updatedOrders }); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - -exports.getOrderStatusHistory = async (req, res) => { - try { - const { orderId } = req.params; - - const order = await OrderHistory.findById(orderId).select("statusHistory"); - if (!order) return res.status(404).json({ message: "Order not found" }); - - res.status(200).json(order.statusHistory); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.getOrdersByStatus = async (req, res) => { - try { - const { status } = req.params; - - const orders = await OrderHistory.find({ orderStatus: status }) - .populate("userId", "name email") // Optionally populate user details - .exec(); - - if (orders.length === 0) - return res - .status(404) - .json({ message: "No orders with the specified status" }); - - res.status(200).json(orders); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; - - - -exports.getAllOrdersForAdmin = async (req, res) => { - try { - const { page = 1, limit = 10 } = req.query; - - const orders = await OrderHistory.find() - .populate("userId", "name email") - .limit(limit * 1) - .skip((page - 1) * limit) - .exec(); - - const count = await OrderHistory.countDocuments(); - - res.status(200).json({ - totalOrders: count, - totalPages: Math.ceil(count / limit), - currentPage: page, - orders, - }); - } catch (err) { - res.status(500).json({ message: "Server Error", error: err.message }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/orderTrackingController.js b/backend/controllers/shop/sub-controllers/orderTrackingController.js deleted file mode 100644 index 2623cbd2..00000000 --- a/backend/controllers/shop/sub-controllers/orderTrackingController.js +++ /dev/null @@ -1,205 +0,0 @@ -const OrderTracking = require("../../../model/shop/sub-model/OrderTracking"); - -// Create new order tracking information -exports.createOrderTracking = async (req, res) => { - try { - const orderTracking = new OrderTracking(req.body); - await orderTracking.save(); - res.status(201).json(orderTracking); - } catch (error) { - res.status(400).json({ message: error.message }); - } -}; - - -// Retrieve tracking information for a specific order -exports.getOrderTracking = async (req, res) => { - try { - const orderTracking = await OrderTracking.findOne({ - orderId: req.params.orderId, - }); - if (!orderTracking) { - return res.status(404).json({ message: "Order tracking not found" }); - } - res.status(200).json(orderTracking); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Update tracking information for an order -exports.updateOrderTracking = async (req, res) => { - try { - const orderTracking = await OrderTracking.findOneAndUpdate( - { orderId: req.params.orderId }, - { ...req.body, updatedAt: Date.now() }, - { new: true } - ); - if (!orderTracking) { - return res.status(404).json({ message: "Order tracking not found" }); - } - res.status(200).json(orderTracking); - } catch (error) { - res.status(400).json({ message: error.message }); - } -}; - - -// Delete tracking information for an order -exports.deleteOrderTracking = async (req, res) => { - try { - const orderTracking = await OrderTracking.findOneAndDelete({ - orderId: req.params.orderId, - }); - if (!orderTracking) { - return res.status(404).json({ message: "Order tracking not found" }); - } - res.status(200).json({ message: "Order tracking deleted successfully" }); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Retrieve all order tracking information -exports.getAllOrderTrackings = async (req, res) => { - try { - const orderTrackings = await OrderTracking.find({}); - res.status(200).json(orderTrackings); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Retrieve order tracking information filtered by status -exports.getOrdersByStatus = async (req, res) => { - try { - const { status } = req.params; - const orders = await OrderTracking.find({ status }); - res.status(200).json(orders); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Retrieve recently updated orders (within the last 24 hours) -exports.getRecentUpdates = async (req, res) => { - try { - const yesterday = new Date(); - yesterday.setDate(yesterday.getDate() - 1); - - const recentOrders = await OrderTracking.find({ - updatedAt: { $gte: yesterday }, - }); - - res.status(200).json(recentOrders); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Retrieve orders by specific carrier -exports.getOrdersByCarrier = async (req, res) => { - try { - const { carrier } = req.params; - const orders = await OrderTracking.find({ carrier }); - res.status(200).json(orders); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Retrieve orders with estimated delivery within a date range -exports.getOrdersByEstimatedDeliveryRange = async (req, res) => { - try { - const { startDate, endDate } = req.query; - const orders = await OrderTracking.find({ - estimatedDelivery: { - $gte: new Date(startDate), - $lte: new Date(endDate), - }, - }); - res.status(200).json(orders); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -exports.getOverdueOrders = async (req, res) => { - try { - const today = new Date(); - const overdueOrders = await OrderTracking.find({ - estimatedDelivery: { $lt: today }, - status: { $ne: "Delivered" }, - }); - res.status(200).json(overdueOrders); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Bulk update the status of multiple orders -exports.bulkUpdateStatus = async (req, res) => { - try { - const { orderIds, status } = req.body; - const result = await OrderTracking.updateMany( - { orderId: { $in: orderIds } }, - { status, updatedAt: Date.now() } - ); - res - .status(200) - .json({ message: `${result.nModified} orders updated successfully` }); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Retrieve orders updated within a specific date range -exports.getOrdersUpdatedWithinRange = async (req, res) => { - try { - const { startDate, endDate } = req.query; - const orders = await OrderTracking.find({ - updatedAt: { - $gte: new Date(startDate), - $lte: new Date(endDate), - }, - }); - res.status(200).json(orders); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Retrieve orders by a range of tracking numbers -exports.getOrdersByTrackingNumberRange = async (req, res) => { - try { - const { startTrackingNumber, endTrackingNumber } = req.query; - const orders = await OrderTracking.find({ - trackingNumber: { $gte: startTrackingNumber, $lte: endTrackingNumber }, - }); - res.status(200).json(orders); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - - -// Retrieve orders with selected fields -exports.getOrdersWithSelectedFields = async (req, res) => { - try { - const fields = req.query.fields.split(",").join(" "); - const orders = await OrderTracking.find({}, fields); - res.status(200).json(orders); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/paymentController.js b/backend/controllers/shop/sub-controllers/paymentController.js deleted file mode 100644 index 0bc6569d..00000000 --- a/backend/controllers/shop/sub-controllers/paymentController.js +++ /dev/null @@ -1,161 +0,0 @@ -const Payment = require("../models/payment"); - -// Retrieve all payments -const getAllPayments = async (req, res) => { - try { - const payments = await Payment.find(); - res.status(200).json(payments); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -// Retrieve payment by ID -const getPaymentById = async (req, res) => { - try { - const payment = await Payment.findById(req.params.id); - if (!payment) return res.status(404).json({ message: "Payment not found" }); - res.status(200).json(payment); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -// Create a new payment -const createPayment = async (req, res) => { - const { orderId, userId, amount, paymentMethod, transactionId } = req.body; - - const newPayment = new Payment({ - paymentId: `PAY${Date.now()}`, - orderId, - userId, - amount, - paymentMethod, - transactionId, - }); - - try { - const payment = await newPayment.save(); - res.status(201).json(payment); - } catch (error) { - res.status(400).json({ message: error.message }); - } -}; - -// Update payment status -const updatePaymentStatus = async (req, res) => { - const { paymentStatus } = req.body; - try { - const payment = await Payment.findByIdAndUpdate( - req.params.id, - { paymentStatus }, - { new: true } - ); - if (!payment) return res.status(404).json({ message: "Payment not found" }); - res.status(200).json(payment); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; -const Payment = require("../models/payment"); - -// Update Payment Method -const updatePaymentMethod = async (req, res) => { - const { paymentMethod } = req.body; - try { - if (!["Credit Card", "PayPal", "Bank Transfer"].includes(paymentMethod)) { - return res.status(400).json({ message: "Invalid payment method" }); - } - const payment = await Payment.findByIdAndUpdate( - req.params.id, - { paymentMethod }, - { new: true } - ); - if (!payment) return res.status(404).json({ message: "Payment not found" }); - res.status(200).json(payment); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -// Retrieve Payments by Date Range -const getPaymentsByDateRange = async (req, res) => { - const { startDate, endDate } = req.query; - try { - const payments = await Payment.find({ - paymentDate: { - $gte: new Date(startDate), - $lte: new Date(endDate), - }, - }); - if (!payments.length) - return res - .status(404) - .json({ message: "No payments found in this date range" }); - res.status(200).json(payments); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -// Retrieve Payments by Amount Range -const getPaymentsByAmountRange = async (req, res) => { - const { minAmount, maxAmount } = req.query; - try { - const payments = await Payment.find({ - amount: { $gte: minAmount, $lte: maxAmount }, - }); - if (!payments.length) - return res - .status(404) - .json({ message: "No payments found in this amount range" }); - res.status(200).json(payments); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -// Retrieve Payment by Transaction ID -const getPaymentByTransactionId = async (req, res) => { - try { - const payment = await Payment.findOne({ - transactionId: req.params.transactionId, - }); - if (!payment) - return res - .status(404) - .json({ message: "Payment not found with this transaction ID" }); - res.status(200).json(payment); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -// Count Payments by Status -const countPaymentsByStatus = async (req, res) => { - try { - const counts = await Payment.aggregate([ - { - $group: { - _id: "$paymentStatus", - count: { $sum: 1 }, - }, - }, - ]); - res.status(200).json(counts); - } catch (error) { - res.status(500).json({ message: error.message }); - } -}; - -module.exports = { - getAllPayments, - getPaymentById, - createPayment, - updatePaymentStatus, - updatePaymentMethod, - getPaymentsByDateRange, - getPaymentsByAmountRange, - getPaymentByTransactionId, - countPaymentsByStatus, -}; diff --git a/backend/controllers/shop/sub-controllers/referralController.js b/backend/controllers/shop/sub-controllers/referralController.js deleted file mode 100644 index ba4285c3..00000000 --- a/backend/controllers/shop/sub-controllers/referralController.js +++ /dev/null @@ -1,202 +0,0 @@ - -const Referral = require("../../../model/shop/sub-model/Referral"); -const User = require("../../../model/user"); -const { - generateUniqueCode, - validateReferralCodeFormat, -} = require("../../../services/sub-service/referralUtils"); -const { logInfo, logError } = require("../../../services/sub-service/logger"); - -// Create a referral code and handle errors -exports.createReferral = async (req, res) => { - try { - const { referrerId } = req.body; - - const referrer = await User.findById(referrerId); - if (!referrer) { - logError("Referrer not found"); - return res.status(404).json({ message: "Referrer user not found" }); - } - - const existingReferral = await Referral.findOne({ - referrerId, - status: "pending", - }); - if (existingReferral) { - logInfo("Active referral code already exists for this user"); - return res - .status(400) - .json({ message: "Active referral code already exists" }); - } - - const referralCode = generateUniqueCode(); - const newReferral = new Referral({ referrerId, referralCode }); - - await newReferral.save(); - logInfo( - `Referral created for referrerId: ${referrerId}, code: ${referralCode}` - ); - res - .status(201) - .json({ message: "Referral created successfully", referralCode }); - } catch (error) { - logError("Error creating referral", error); - res.status(500).json({ message: "Error creating referral", error }); - } -}; - -// Get referral status -exports.checkReferralStatus = async (req, res) => { - try { - const { code } = req.params; - - if (!validateReferralCodeFormat(code)) { - logError("Invalid referral code format"); - return res.status(400).json({ message: "Invalid referral code format" }); - } - - const referral = await Referral.findOne({ referralCode: code }); - if (!referral) { - logInfo("Referral code not found"); - return res.status(404).json({ message: "Referral code not found" }); - } - - res.status(200).json({ status: referral.status }); - } catch (error) { - logError("Error checking referral status", error); - res.status(500).json({ message: "Error checking referral status", error }); - } -}; - -// Complete a referral process -exports.completeReferral = async (req, res) => { - try { - const { code, refereeId } = req.body; - - if (!validateReferralCodeFormat(code)) { - logError("Invalid referral code format"); - return res.status(400).json({ message: "Invalid referral code format" }); - } - - const referral = await Referral.findOne({ referralCode: code }); - if (!referral) { - logInfo("Referral code not found"); - return res.status(404).json({ message: "Referral code not found" }); - } - - if (referral.status === "completed") { - logInfo("Referral code already used"); - return res.status(400).json({ message: "Referral code already used" }); - } - - const referee = await User.findById(refereeId); - if (!referee) { - logInfo("Referee user not found"); - return res.status(404).json({ message: "Referee user not found" }); - } - - if (referral.referrerId.toString() === refereeId) { - logInfo("Cannot use your own referral code"); - return res - .status(400) - .json({ message: "Cannot use your own referral code" }); - } - - referral.status = "completed"; - referral.refereeId = refereeId; - await referral.save(); - logInfo(`Referral code ${code} completed successfully by ${refereeId}`); - - res.status(200).json({ message: "Referral completed successfully" }); - } catch (error) { - logError("Error completing referral", error); - res.status(500).json({ message: "Error completing referral", error }); - } -}; - -// Get referrals for specific referrer with extra filters and pagination -exports.getReferralsByReferrer = async (req, res) => { - try { - const { referrerId } = req.params; - const { status, page = 1, limit = 10 } = req.query; - - const referrer = await User.findById(referrerId); - if (!referrer) { - logError("Referrer user not found"); - return res.status(404).json({ message: "Referrer user not found" }); - } - - const filter = { referrerId }; - if (status) filter.status = status; - - const referrals = await Referral.find(filter) - .skip((page - 1) * limit) - .limit(parseInt(limit)); - const totalCount = await Referral.countDocuments(filter); - - res.status(200).json({ - referrals, - totalPages: Math.ceil(totalCount / limit), - currentPage: page, - }); - } catch (error) { - logError("Error retrieving referrals by referrer", error); - res.status(500).json({ message: "Error retrieving referrals", error }); - } -}; - -// List all referrals for admin with advanced filtering and sorting -exports.listAllReferrals = async (req, res) => { - try { - const { - page = 1, - limit = 10, - sortBy = "createdAt", - order = "desc", - } = req.query; - - const referrals = await Referral.find() - .sort({ [sortBy]: order === "asc" ? 1 : -1 }) - .skip((page - 1) * limit) - .limit(parseInt(limit)); - const totalCount = await Referral.countDocuments(); - - res.status(200).json({ - referrals, - totalPages: Math.ceil(totalCount / limit), - currentPage: page, - }); - } catch (error) { - logError("Error retrieving all referrals", error); - res.status(500).json({ message: "Error retrieving referrals", error }); - } -}; - -// Cancel a pending referral -exports.cancelReferral = async (req, res) => { - try { - const { code } = req.body; - - const referral = await Referral.findOne({ referralCode: code }); - if (!referral) { - logInfo("Referral code not found"); - return res.status(404).json({ message: "Referral code not found" }); - } - - if (referral.status !== "pending") { - logInfo("Only pending referrals can be canceled"); - return res - .status(400) - .json({ message: "Only pending referrals can be canceled" }); - } - - referral.status = "canceled"; - await referral.save(); - logInfo(`Referral code ${code} canceled successfully`); - - res.status(200).json({ message: "Referral canceled successfully" }); - } catch (error) { - logError("Error canceling referral", error); - res.status(500).json({ message: "Error canceling referral", error }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/returnController.js b/backend/controllers/shop/sub-controllers/returnController.js deleted file mode 100644 index 21da8d57..00000000 --- a/backend/controllers/shop/sub-controllers/returnController.js +++ /dev/null @@ -1,229 +0,0 @@ - -const ReturnProduct = require('../models/ReturnProduct'); -const Product = require('../models/Product'); -const User = require('../models/User'); - -// Create Return (POST /api/returns) -exports.createReturn = async (req, res) => { - try { - const { productId, returnDate, condition } = req.body; - const userId = req.user.id; // Assuming user authentication is in place - - const product = await Product.findById(productId); - if (!product) { - return res.status(404).json({ message: 'Product not found.' }); - } - - // Check if the product has already been returned - const existingReturn = await ReturnProduct.findOne({ productId, userId, status: 'returned' }); - if (existingReturn) { - return res.status(400).json({ message: 'Product has already been returned.' }); - } - - const returnRequest = new ReturnProduct({ - productId, - userId, - returnDate, - condition, - status: 'pending' - }); - - await returnRequest.save(); - res.status(201).json({ message: 'Return request created successfully.', returnRequest }); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } -}; - -// Update Return Status (PATCH /api/returns/:id) -exports.updateReturnStatus = async (req, res) => { - try { - const { status } = req.body; - const returnId = req.params.id; - - if (!['approved', 'rejected'].includes(status)) { - return res.status(400).json({ message: 'Invalid status.' }); - } - - const returnRequest = await ReturnProduct.findById(returnId); - if (!returnRequest) { - return res.status(404).json({ message: 'Return request not found.' }); - } - - // Ensure that only admins can update the status - if (!req.user.isAdmin) { - return res.status(403).json({ message: 'Admin access required.' }); - } - - returnRequest.status = status; - returnRequest.updatedAt = Date.now(); - await returnRequest.save(); - - res.status(200).json({ message: 'Return status updated successfully.', returnRequest }); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } -}; - -// Get Return Information (GET /api/returns/:id) -exports.getReturnInformation = async (req, res) => { - try { - const returnId = req.params.id; - const returnRequest = await ReturnProduct.findById(returnId) - .populate('productId') - .populate('userId'); - - if (!returnRequest) { - return res.status(404).json({ message: 'Return request not found.' }); - } - - // Check if the user is authorized to view return details - if (req.user.id !== returnRequest.userId.toString() && !req.user.isAdmin) { - return res.status(403).json({ message: 'Unauthorized access.' }); - } - - res.status(200).json(returnRequest); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } -}; - -// Get User’s Return History (GET /api/returns/user/:userId) -exports.getUserReturnHistory = async (req, res) => { - try { - const userId = req.params.userId; - - if (req.user.id !== userId && !req.user.isAdmin) { - return res.status(403).json({ message: 'Unauthorized access.' }); - } - - const returnHistory = await ReturnProduct.find({ userId }) - .populate('productId') - .populate('userId'); - - if (!returnHistory.length) { - return res.status(404).json({ message: 'No return history found.' }); - } - - res.status(200).json(returnHistory); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } -}; - -// Get All Pending Returns (GET /api/returns/pending) -exports.getPendingReturns = async (req, res) => { - try { - if (!req.user.isAdmin) { - return res.status(403).json({ message: 'Admin access required.' }); - } - - const pendingReturns = await ReturnProduct.find({ status: 'pending' }) - .populate('productId') - .populate('userId'); - - if (!pendingReturns.length) { - return res.status(404).json({ message: 'No pending returns found.' }); - } - - res.status(200).json(pendingReturns); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } -}; - -// Cancel Return Request (PATCH /api/returns/cancel/:id) -exports.cancelReturnRequest = async (req, res) => { - try { - const returnId = req.params.id; - const returnRequest = await ReturnProduct.findById(returnId); - - if (!returnRequest) { - return res.status(404).json({ message: 'Return request not found.' }); - } - - // Check if the return request is still pending - if (returnRequest.status !== 'pending') { - return res.status(400).json({ message: 'Return request cannot be canceled once it is processed.' }); - } - - // Ensure that the user is the one who made the return request - if (returnRequest.userId.toString() !== req.user.id) { - return res.status(403).json({ message: 'You are not authorized to cancel this return request.' }); - } - - returnRequest.status = 'canceled'; - returnRequest.updatedAt = Date.now(); - await returnRequest.save(); - - res.status(200).json({ message: 'Return request canceled successfully.', returnRequest }); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } - }; - - // Get All Returned Products (GET /api/returns/returned) -exports.getAllReturnedProducts = async (req, res) => { - try { - if (!req.user.isAdmin) { - return res.status(403).json({ message: 'Admin access required.' }); - } - - const returnedProducts = await ReturnProduct.find({ status: 'returned' }) - .populate('productId') - .populate('userId'); - - if (!returnedProducts.length) { - return res.status(404).json({ message: 'No returned products found.' }); - } - - res.status(200).json(returnedProducts); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } - }; - - // Get All Damaged Products (GET /api/returns/damaged) -exports.getAllDamagedProducts = async (req, res) => { - try { - if (!req.user.isAdmin) { - return res.status(403).json({ message: 'Admin access required.' }); - } - - const damagedProducts = await ReturnProduct.find({ condition: 'damaged' }) - .populate('productId') - .populate('userId'); - - if (!damagedProducts.length) { - return res.status(404).json({ message: 'No damaged products found.' }); - } - - res.status(200).json(damagedProducts); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } - }; - - // Get Return Requests for a Specific Product (GET /api/returns/product/:productId) -exports.getReturnRequestsForProduct = async (req, res) => { - try { - const { productId } = req.params; - - if (!req.user.isAdmin) { - return res.status(403).json({ message: 'Admin access required.' }); - } - - const returnRequests = await ReturnProduct.find({ productId }) - .populate('productId') - .populate('userId'); - - if (!returnRequests.length) { - return res.status(404).json({ message: 'No return requests found for this product.' }); - } - - res.status(200).json(returnRequests); - } catch (err) { - res.status(500).json({ message: 'Server error.', error: err.message }); - } - }; - \ No newline at end of file diff --git a/backend/controllers/shop/sub-controllers/shippingAddressController.js b/backend/controllers/shop/sub-controllers/shippingAddressController.js deleted file mode 100644 index b69f1acd..00000000 --- a/backend/controllers/shop/sub-controllers/shippingAddressController.js +++ /dev/null @@ -1,249 +0,0 @@ -// controllers/shippingAddressController.js -const ShippingAddress = require("../../../model/shop/sub-model/ShippingAddress"); - -// Add a new shipping address -exports.addShippingAddress = async (req, res) => { - try { - const { addressLine1, addressLine2, city, state, postalCode, country } = - req.body; - - const newAddress = new ShippingAddress({ - addressLine1, - addressLine2, - city, - state, - postalCode, - country, - user: req.user._id, // assuming user authentication middleware is in place - }); - - await newAddress.save(); - res - .status(201) - .json({ - message: "Shipping address added successfully", - address: newAddress, - }); - } catch (error) { - res.status(500).json({ message: "Server error", error: error.message }); - } -}; - -// Get all shipping addresses for a user -exports.getShippingAddresses = async (req, res) => { - try { - const addresses = await ShippingAddress.find({ user: req.user._id }); - res.status(200).json(addresses); - } catch (error) { - res.status(500).json({ message: "Server error", error: error.message }); - } -}; - -// Update a specific shipping address -exports.updateShippingAddress = async (req, res) => { - try { - const { id } = req.params; - const { addressLine1, addressLine2, city, state, postalCode, country } = - req.body; - - const updatedAddress = await ShippingAddress.findOneAndUpdate( - { _id: id, user: req.user._id }, - { addressLine1, addressLine2, city, state, postalCode, country }, - { new: true } - ); - - if (!updatedAddress) { - return res - .status(404) - .json({ message: "Address not found or not authorized" }); - } - - res - .status(200) - .json({ - message: "Shipping address updated successfully", - address: updatedAddress, - }); - } catch (error) { - res.status(500).json({ message: "Server error", error: error.message }); - } -}; - -// Delete a specific shipping address -exports.deleteShippingAddress = async (req, res) => { - try { - const { id } = req.params; - - const deletedAddress = await ShippingAddress.findOneAndDelete({ - _id: id, - user: req.user._id, - }); - - if (!deletedAddress) { - return res - .status(404) - .json({ message: "Address not found or not authorized" }); - } - - res.status(200).json({ message: "Shipping address deleted successfully" }); - } catch (error) { - res.status(500).json({ message: "Server error", error: error.message }); - } -}; - -// Set a primary shipping address -exports.setPrimaryAddress = async (req, res) => { - try { - const { id } = req.params; - - // Find the user's addresses and set all addresses to not primary - await ShippingAddress.updateMany( - { user: req.user._id }, - { $set: { isPrimary: false } } - ); - - // Set the specified address as primary - const primaryAddress = await ShippingAddress.findOneAndUpdate( - { _id: id, user: req.user._id }, - { $set: { isPrimary: true } }, - { new: true } - ); - - if (!primaryAddress) { - return res - .status(404) - .json({ message: "Address not found or not authorized" }); - } - - res - .status(200) - .json({ - message: "Primary address set successfully", - address: primaryAddress, - }); - } catch (error) { - res.status(500).json({ message: "Server error", error: error.message }); - } -}; - -// Get a specific shipping address by ID -exports.getShippingAddressById = async (req, res) => { - try { - const { id } = req.params; - - const address = await ShippingAddress.findOne({ - _id: id, - user: req.user._id, - }); - - if (!address) { - return res - .status(404) - .json({ message: "Address not found or not authorized" }); - } - - res.status(200).json({ address }); - } catch (error) { - res.status(500).json({ message: "Server error", error: error.message }); - } -}; - -// Get primary shipping address -exports.getPrimaryAddress = async (req, res) => { - try { - const primaryAddress = await ShippingAddress.findOne({ - user: req.user._id, - isPrimary: true, - }); - - if (!primaryAddress) { - return res.status(404).json({ message: "No primary address found" }); - } - - res.status(200).json({ address: primaryAddress }); - } catch (error) { - res.status(500).json({ message: "Server error", error: error.message }); - } -}; - - - -// Set a default address -exports.setDefaultAddress = async (req, res) => { - try { - const { id } = req.params; - - // Reset all addresses' default status for the user - await ShippingAddress.updateMany( - { user: req.user._id }, - { $set: { isDefault: false } } - ); - - // Set the specified address as default - const defaultAddress = await ShippingAddress.findOneAndUpdate( - { _id: id, user: req.user._id }, - { $set: { isDefault: true } }, - { new: true } - ); - - if (!defaultAddress) { - return res.status(404).json({ message: 'Address not found or not authorized' }); - } - - res.status(200).json({ message: 'Default address set successfully', address: defaultAddress }); - } catch (error) { - res.status(500).json({ message: 'Server error', error: error.message }); - } -}; - -// Search addresses by field (e.g., city, state, country) -exports.searchAddresses = async (req, res) => { - try { - const { city, state, country } = req.query; - const searchCriteria = { user: req.user._id }; - - if (city) searchCriteria.city = city; - if (state) searchCriteria.state = state; - if (country) searchCriteria.country = country; - - const addresses = await ShippingAddress.find(searchCriteria); - res.status(200).json(addresses); - } catch (error) { - res.status(500).json({ message: 'Server error', error: error.message }); - } -}; - -// Archive a specific address -exports.archiveAddress = async (req, res) => { - try { - const { id } = req.params; - - const archivedAddress = await ShippingAddress.findOneAndUpdate( - { _id: id, user: req.user._id }, - { $set: { isArchived: true } }, - { new: true } - ); - - if (!archivedAddress) { - return res.status(404).json({ message: 'Address not found or not authorized' }); - } - - res.status(200).json({ message: 'Address archived successfully', address: archivedAddress }); - } catch (error) { - res.status(500).json({ message: 'Server error', error: error.message }); - } -}; - -// Retrieve only active (non-archived) addresses -exports.getActiveAddresses = async (req, res) => { - try { - const activeAddresses = await ShippingAddress.find({ - user: req.user._id, - isArchived: { $ne: true }, - }); - - res.status(200).json(activeAddresses); - } catch (error) { - res.status(500).json({ message: 'Server error', error: error.message }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/supplierController.js b/backend/controllers/shop/sub-controllers/supplierController.js deleted file mode 100644 index c088b5b5..00000000 --- a/backend/controllers/shop/sub-controllers/supplierController.js +++ /dev/null @@ -1,176 +0,0 @@ -const Supplier = require("../models/Supplier"); - -exports.createSupplier = async (req, res) => { - try { - const { name, contactInfo, address, productsSupplied, status } = req.body; - const supplier = new Supplier({ - name, - contactInfo, - address, - productsSupplied, - status, - }); - await supplier.save(); - res.status(201).json(supplier); - } catch (err) { - res.status(500).json({ message: "Error creating supplier", error: err }); - } -}; - -// Get all Suppliers with pagination and sorting -exports.getAllSuppliers = async (req, res) => { - try { - const { page = 1, limit = 10, sort = "createdAt" } = req.query; - const suppliers = await Supplier.find() - .sort(sort) - .skip((page - 1) * limit) - .limit(Number(limit)); - res.json(suppliers); - } catch (err) { - res.status(500).json({ message: "Error fetching suppliers", error: err }); - } -}; - -// Get a Supplier by ID -exports.getSupplierById = async (req, res) => { - try { - const supplier = await Supplier.findById(req.params.id); - if (!supplier) { - return res.status(404).json({ message: "Supplier not found" }); - } - res.json(supplier); - } catch (err) { - res.status(500).json({ message: "Error fetching supplier", error: err }); - } -}; - -// Update a Supplier -exports.updateSupplier = async (req, res) => { - try { - const { name, contactInfo, address, productsSupplied, status } = req.body; - const supplier = await Supplier.findByIdAndUpdate( - req.params.id, - { - name, - contactInfo, - address, - productsSupplied, - status, - updatedAt: Date.now(), - }, - { new: true } - ); - if (!supplier) { - return res.status(404).json({ message: "Supplier not found" }); - } - res.json(supplier); - } catch (err) { - res.status(500).json({ message: "Error updating supplier", error: err }); - } -}; - -// Soft delete a Supplier (set status to inactive) -exports.deleteSupplier = async (req, res) => { - try { - const supplier = await Supplier.findByIdAndUpdate( - req.params.id, - { status: "inactive" }, - { new: true } - ); - if (!supplier) { - return res.status(404).json({ message: "Supplier not found" }); - } - res.json(supplier); - } catch (err) { - res.status(500).json({ message: "Error deleting supplier", error: err }); - } -}; - -const Supplier = require("../models/Supplier"); -const Product = require("../models/Product"); // Assuming there's a Product model - -// Add a product to a supplier -exports.addProductToSupplier = async (req, res) => { - try { - const { productId } = req.body; - const supplier = await Supplier.findById(req.params.id); - if (!supplier) { - return res.status(404).json({ message: "Supplier not found" }); - } - - supplier.productsSupplied.push(productId); - await supplier.save(); - - res.status(200).json(supplier); - } catch (err) { - res - .status(500) - .json({ message: "Error adding product to supplier", error: err }); - } -}; - -// Remove a product from a supplier -exports.removeProductFromSupplier = async (req, res) => { - try { - const { productId } = req.body; - const supplier = await Supplier.findById(req.params.id); - if (!supplier) { - return res.status(404).json({ message: "Supplier not found" }); - } - - supplier.productsSupplied = supplier.productsSupplied.filter( - (product) => product.toString() !== productId - ); - await supplier.save(); - - res.status(200).json(supplier); - } catch (err) { - res - .status(500) - .json({ message: "Error removing product from supplier", error: err }); - } -}; - -// Get all products supplied by a supplier -exports.getProductsSupplied = async (req, res) => { - try { - const supplier = await Supplier.findById(req.params.id).populate( - "productsSupplied" - ); - if (!supplier) { - return res.status(404).json({ message: "Supplier not found" }); - } - res.json(supplier.productsSupplied); - } catch (err) { - res.status(500).json({ message: "Error fetching products", error: err }); - } -}; - -exports.searchSuppliers = async (req, res) => { - try { - const { name, status, email, phone } = req.query; - const query = {}; - - if (name) query.name = { $regex: name, $options: "i" }; - if (status) query.status = status; - if (email) query["contactInfo.email"] = email; - if (phone) query["contactInfo.phone"] = phone; - - const suppliers = await Supplier.find(query); - res.json(suppliers); - } catch (err) { - res.status(500).json({ message: "Error searching suppliers", error: err }); - } -}; - -exports.getSuppliersByStatus = async (req, res) => { - try { - const { status } = req.params; - const suppliers = await Supplier.find({ status }); - res.json(suppliers); - } catch (err) { - res - .status(500) - .json({ message: "Error fetching suppliers by status", error: err }); - } -}; diff --git a/backend/controllers/shop/sub-controllers/ticketController.js b/backend/controllers/shop/sub-controllers/ticketController.js deleted file mode 100644 index 2fa3385e..00000000 --- a/backend/controllers/shop/sub-controllers/ticketController.js +++ /dev/null @@ -1,277 +0,0 @@ -const Ticket = require("../../../model/shop/sub-model/TIcket"); -const User = require("../../../model/user"); -const Agent = require("../models/Agent"); - -const asyncHandler = require("express-async-handler"); - -// Create a new ticket -const createTicket = asyncHandler(async (req, res) => { - const { userId, subject, description, priority } = req.body; - - if (!userId || !subject || !description || !priority) { - return res.status(400).json({ message: "Missing required fields" }); - } - - const ticketId = `TKT-${Date.now()}`; - - const ticket = await Ticket.create({ - ticketId, - userId, - subject, - description, - priority, - }); - - res.status(201).json(ticket); -}); - -// Fetch ticket details by ticketId -const getTicketDetails = asyncHandler(async (req, res) => { - const { ticketId } = req.params; - - const ticket = await Ticket.findOne({ ticketId }) - .populate("userId") - .populate("assignedAgentId"); - - if (!ticket) { - return res.status(404).json({ message: "Ticket not found" }); - } - - res.status(200).json(ticket); -}); - -// Fetch all tickets for a user -const getUserTickets = asyncHandler(async (req, res) => { - const { userId } = req.params; - - const tickets = await Ticket.find({ userId }).populate("assignedAgentId"); - - if (tickets.length === 0) { - return res.status(404).json({ message: "No tickets found for this user" }); - } - - res.status(200).json(tickets); -}); - -// Fetch all tickets assigned to an agent -const getAssignedTickets = asyncHandler(async (req, res) => { - const { agentId } = req.params; - - const tickets = await Ticket.find({ assignedAgentId: agentId }); - - if (tickets.length === 0) { - return res - .status(404) - .json({ message: "No tickets assigned to this agent" }); - } - - res.status(200).json(tickets); -}); - -// Update ticket status -const updateTicketStatus = asyncHandler(async (req, res) => { - const { ticketId } = req.params; - const { status } = req.body; - - if ( - !status || - !["open", "in-progress", "resolved", "closed"].includes(status) - ) { - return res.status(400).json({ message: "Invalid status" }); - } - - const ticket = await Ticket.findOne({ ticketId }); - - if (!ticket) { - return res.status(404).json({ message: "Ticket not found" }); - } - - if ( - ticket.assignedAgentId && - ticket.assignedAgentId.toString() !== req.user.id - ) { - return res - .status(403) - .json({ message: "You are not authorized to update this ticket" }); - } - - // Only allow status changes from 'open' to 'in-progress', 'in-progress' to 'resolved', and 'resolved' to 'closed' - const validStatusChanges = { - open: ["in-progress"], - "in-progress": ["resolved"], - resolved: ["closed"], - }; - - if (!validStatusChanges[ticket.status]?.includes(status)) { - return res - .status(400) - .json({ message: `Cannot move from ${ticket.status} to ${status}` }); - } - - ticket.status = status; - ticket.updatedAt = Date.now(); - - await ticket.save(); - - res.status(200).json(ticket); -}); - -// Assign a ticket to a support agent -const assignTicket = asyncHandler(async (req, res) => { - const { ticketId } = req.params; - const { agentId } = req.body; - - if (!agentId) { - return res.status(400).json({ message: "Agent ID is required" }); - } - - const ticket = await Ticket.findOne({ ticketId }); - - if (!ticket) { - return res.status(404).json({ message: "Ticket not found" }); - } - - const agent = await Agent.findById(agentId); - - if (!agent) { - return res.status(404).json({ message: "Agent not found" }); - } - - ticket.assignedAgentId = agentId; - ticket.updatedAt = Date.now(); - - await ticket.save(); - - res.status(200).json(ticket); -}); - -// Close a ticket (status "closed") -const closeTicket = asyncHandler(async (req, res) => { - const { ticketId } = req.params; - - const ticket = await Ticket.findOne({ ticketId }); - - if (!ticket) { - return res.status(404).json({ message: "Ticket not found" }); - } - - if (ticket.status === "closed") { - return res.status(400).json({ message: "Ticket is already closed" }); - } - - ticket.status = "closed"; - ticket.updatedAt = Date.now(); - - await ticket.save(); - - res.status(200).json(ticket); -}); - -// Delete a ticket (soft delete or permanent) -const deleteTicket = asyncHandler(async (req, res) => { - const { ticketId } = req.params; - - const ticket = await Ticket.findOne({ ticketId }); - - if (!ticket) { - return res.status(404).json({ message: "Ticket not found" }); - } - - // You can choose to either permanently delete or soft delete - await ticket.remove(); // Soft delete - - res.status(200).json({ message: "Ticket deleted successfully" }); -}); - -// Get all tickets (Admin only) -const getAllTickets = asyncHandler(async (req, res) => { - const tickets = await Ticket.find() - .populate("assignedAgentId") - .populate("userId"); - - if (tickets.length === 0) { - return res.status(404).json({ message: "No tickets found" }); - } - - res.status(200).json(tickets); -}); - -// Update ticket priority -const updateTicketPriority = asyncHandler(async (req, res) => { - const { ticketId } = req.params; - const { priority } = req.body; - - if (!["low", "medium", "high"].includes(priority)) { - return res.status(400).json({ message: "Invalid priority level" }); - } - - const ticket = await Ticket.findOne({ ticketId }); - - if (!ticket) { - return res.status(404).json({ message: "Ticket not found" }); - } - - ticket.priority = priority; - ticket.updatedAt = Date.now(); - - await ticket.save(); - - res.status(200).json(ticket); -}); - -// Fetch tickets by status -const getTicketsByStatus = asyncHandler(async (req, res) => { - const { status } = req.params; - - if (!["open", "in-progress", "resolved", "closed"].includes(status)) { - return res.status(400).json({ message: "Invalid status" }); - } - - const tickets = await Ticket.find({ status }) - .populate("assignedAgentId") - .populate("userId"); - - if (tickets.length === 0) { - return res - .status(404) - .json({ message: `No tickets with status: ${status}` }); - } - - res.status(200).json(tickets); -}); - -// Fetch tickets by priority -const getTicketsByPriority = asyncHandler(async (req, res) => { - const { priority } = req.params; - - if (!["low", "medium", "high"].includes(priority)) { - return res.status(400).json({ message: "Invalid priority level" }); - } - - const tickets = await Ticket.find({ priority }) - .populate("assignedAgentId") - .populate("userId"); - - if (tickets.length === 0) { - return res - .status(404) - .json({ message: `No tickets with priority: ${priority}` }); - } - - res.status(200).json(tickets); -}); - -module.exports = { - createTicket, - getTicketDetails, - getUserTickets, - getAssignedTickets, - updateTicketStatus, - assignTicket, - closeTicket, - deleteTicket, - getAllTickets, - updateTicketPriority, - getTicketsByStatus, - getTicketsByPriority, -}; diff --git a/backend/controllers/shop/sub-controllers/warehouseController.js b/backend/controllers/shop/sub-controllers/warehouseController.js deleted file mode 100644 index 2e8dbfe4..00000000 --- a/backend/controllers/shop/sub-controllers/warehouseController.js +++ /dev/null @@ -1,330 +0,0 @@ -const Warehouse = require("../../../model/shop/sub-model/Warehouse"); -const InventoryItem = require("../../../model/shop/sub-model/InventoryModel"); - -// 1. Create Warehouse Logic -exports.createWarehouse = async (req, res) => { - try { - const { - warehouseId, - warehouseName, - address, - capacity, - currentOccupancy, - inventoryItems, - contactInfo, - } = req.body; - - // Validate unique Warehouse Name and Warehouse ID - const existingWarehouse = await Warehouse.findOne({ - $or: [{ warehouseId }, { warehouseName }], - }); - if (existingWarehouse) { - return res - .status(400) - .json({ message: "Warehouse ID or Name must be unique" }); - } - - // Create new warehouse - const warehouse = new Warehouse({ - warehouseId, - warehouseName, - address, - capacity, - currentOccupancy, - inventoryItems, - contactInfo, - lastUpdated: new Date(), - }); - - await warehouse.save(); - - return res - .status(201) - .json({ message: "Warehouse created successfully", warehouse }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 2. Update Warehouse Logic -exports.updateWarehouse = async (req, res) => { - try { - const { warehouseId } = req.params; - const { - warehouseName, - address, - capacity, - currentOccupancy, - inventoryItems, - contactInfo, - } = req.body; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - // Update warehouse data - warehouse.warehouseName = warehouseName || warehouse.warehouseName; - warehouse.address = address || warehouse.address; - warehouse.capacity = capacity || warehouse.capacity; - warehouse.currentOccupancy = currentOccupancy || warehouse.currentOccupancy; - warehouse.inventoryItems = inventoryItems || warehouse.inventoryItems; - warehouse.contactInfo = contactInfo || warehouse.contactInfo; - warehouse.lastUpdated = new Date(); - - await warehouse.save(); - - return res - .status(200) - .json({ message: "Warehouse updated successfully", warehouse }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 3. Get Warehouse Inventory -exports.getWarehouseInventory = async (req, res) => { - try { - const { warehouseId } = req.params; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - return res.status(200).json({ inventoryItems: warehouse.inventoryItems }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 4. Check Warehouse Capacity -exports.checkWarehouseCapacity = async (req, res) => { - try { - const { warehouseId } = req.params; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - if (warehouse.currentOccupancy > warehouse.capacity) { - return res.status(400).json({ - message: "Current Occupancy exceeds Warehouse Capacity", - status: "Over Capacity", - currentOccupancy: warehouse.currentOccupancy, - capacity: warehouse.capacity, - }); - } - - return res.status(200).json({ - message: "Warehouse is within capacity", - status: "Within Capacity", - currentOccupancy: warehouse.currentOccupancy, - capacity: warehouse.capacity, - }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 5. Delete Warehouse Logic -exports.deleteWarehouse = async (req, res) => { - try { - const { warehouseId } = req.params; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - await warehouse.remove(); - - return res.status(200).json({ message: "Warehouse deleted successfully" }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 6. Get All Warehouses -exports.getAllWarehouses = async (req, res) => { - try { - const warehouses = await Warehouse.find(); - return res.status(200).json(warehouses); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 7. Search Warehouse by Name or ID -exports.searchWarehouse = async (req, res) => { - try { - const { query } = req.params; - const warehouses = await Warehouse.find({ - $or: [ - { warehouseId: { $regex: query, $options: "i" } }, - { warehouseName: { $regex: query, $options: "i" } }, - ], - }); - - if (warehouses.length === 0) { - return res.status(404).json({ message: "No matching warehouses found" }); - } - - return res.status(200).json(warehouses); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 8. Add New Inventory Item -exports.addInventoryItem = async (req, res) => { - try { - const { warehouseId } = req.params; - const { itemName, quantity, price } = req.body; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - // Create new inventory item - const inventoryItem = new InventoryItem({ - itemName, - quantity, - price, - warehouseId, - }); - - await inventoryItem.save(); - - // Add the inventory item to the warehouse - warehouse.inventoryItems.push(inventoryItem); - await warehouse.save(); - - return res - .status(201) - .json({ message: "Inventory item added successfully", inventoryItem }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 9. Update Inventory Item -exports.updateInventoryItem = async (req, res) => { - try { - const { warehouseId, itemId } = req.params; - const { quantity, price } = req.body; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - const inventoryItem = await InventoryItem.findOne({ - _id: itemId, - warehouseId, - }); - if (!inventoryItem) { - return res.status(404).json({ message: "Inventory item not found" }); - } - - inventoryItem.quantity = quantity || inventoryItem.quantity; - inventoryItem.price = price || inventoryItem.price; - - await inventoryItem.save(); - - return res - .status(200) - .json({ message: "Inventory item updated successfully", inventoryItem }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 10. Get Inventory Item by ID -exports.getInventoryItemById = async (req, res) => { - try { - const { warehouseId, itemId } = req.params; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - const inventoryItem = await InventoryItem.findOne({ - _id: itemId, - warehouseId, - }); - if (!inventoryItem) { - return res.status(404).json({ message: "Inventory item not found" }); - } - - return res.status(200).json({ inventoryItem }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 11. Delete Inventory Item -exports.deleteInventoryItem = async (req, res) => { - try { - const { warehouseId, itemId } = req.params; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - const inventoryItem = await InventoryItem.findOne({ - _id: itemId, - warehouseId, - }); - if (!inventoryItem) { - return res.status(404).json({ message: "Inventory item not found" }); - } - - // Remove item from the warehouse - warehouse.inventoryItems = warehouse.inventoryItems.filter( - (item) => item._id.toString() !== itemId - ); - await warehouse.save(); - - // Delete the inventory item - await inventoryItem.remove(); - - return res - .status(200) - .json({ message: "Inventory item deleted successfully" }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; - -// 12. Check Stock Level of Item -exports.checkStockLevel = async (req, res) => { - try { - const { warehouseId, itemId } = req.params; - - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - - const inventoryItem = await InventoryItem.findOne({ - _id: itemId, - warehouseId, - }); - if (!inventoryItem) { - return res.status(404).json({ message: "Inventory item not found" }); - } - - return res.status(200).json({ - message: "Inventory item stock level", - stockLevel: inventoryItem.quantity, - }); - } catch (error) { - return res.status(500).json({ message: "Server error", error }); - } -}; diff --git a/backend/middleware/sub-ware/agentMiddleware.js b/backend/middleware/sub-ware/agentMiddleware.js deleted file mode 100644 index 63144e91..00000000 --- a/backend/middleware/sub-ware/agentMiddleware.js +++ /dev/null @@ -1,23 +0,0 @@ -const Agent = require('../models/Agent'); - -// Middleware to check if the agent exists -exports.checkAgentExists = async (req, res, next) => { - try { - const agent = await Agent.findById(req.params.id); - if (!agent) { - return res.status(404).json({ message: 'Agent not found' }); - } - next(); - } catch (err) { - res.status(400).json({ message: 'Error checking agent existence', error: err }); - } -}; - -// Middleware to check agent permissions (e.g., only admins can assign tickets) -exports.checkPermissions = (req, res, next) => { - const agentRole = req.user.role; // Assuming user role is stored in the request context - if (agentRole !== 'admin') { - return res.status(403).json({ message: 'Permission denied' }); - } - next(); -}; diff --git a/backend/middleware/sub-ware/authSupplierMiddleware.js b/backend/middleware/sub-ware/authSupplierMiddleware.js deleted file mode 100644 index adce51f9..00000000 --- a/backend/middleware/sub-ware/authSupplierMiddleware.js +++ /dev/null @@ -1,10 +0,0 @@ -const isAdmin = (req, res, next) => { - // Assuming user object is attached to request after authentication - if (req.user && req.user.role === "admin") { - next(); - } else { - return res.status(403).json({ message: "Access forbidden: Admins only" }); - } -}; - -module.exports = isAdmin; diff --git a/backend/middleware/sub-ware/giftCardMiddleware.js b/backend/middleware/sub-ware/giftCardMiddleware.js deleted file mode 100644 index 3c7782fa..00000000 --- a/backend/middleware/sub-ware/giftCardMiddleware.js +++ /dev/null @@ -1,28 +0,0 @@ -const GiftCard = require("../../model/shop/sub-model/GiftCard"); - -// Validate if gift card is active and not expired -exports.validateGiftCard = async (req, res, next) => { - const { cardNumber } = req.body; - - const giftCard = await GiftCard.findOne({ cardNumber }); - - if (!giftCard) { - return res.status(404).json({ message: "Gift card not found" }); - } - - if (giftCard.status === "redeemed") { - return res.status(400).json({ message: "Gift card already redeemed" }); - } - - if (giftCard.status === "expired") { - return res.status(400).json({ message: "Gift card has expired" }); - } - - if (giftCard.expiryDate < new Date()) { - giftCard.status = "expired"; - await giftCard.save(); - return res.status(400).json({ message: "Gift card has expired" }); - } - - next(); -}; diff --git a/backend/middleware/sub-ware/inventoryMiddleware.js b/backend/middleware/sub-ware/inventoryMiddleware.js deleted file mode 100644 index 16638dd9..00000000 --- a/backend/middleware/sub-ware/inventoryMiddleware.js +++ /dev/null @@ -1,38 +0,0 @@ -const Inventory = require("../../model/shop/sub-model/InventoryModel"); -const Product = require("../../model/shop/product"); - -// Middleware to validate if product exists before creating inventory -exports.validateProductExistence = async (req, res, next) => { - const { productId } = req.body; - - const product = await Product.findById(productId); - if (!product) { - return res.status(400).json({ message: "Product not found" }); - } - - next(); -}; - -// Middleware to ensure valid stock level when updating -exports.validateStockLevel = (req, res, next) => { - const { newStockLevel } = req.body; - - if (newStockLevel < 0) { - return res.status(400).json({ message: "Stock level cannot be negative" }); - } - - next(); -}; - -// Middleware to ensure reorder level is logical (not negative) -exports.validateReorderLevel = (req, res, next) => { - const { reorderLevel } = req.body; - - if (reorderLevel < 0) { - return res - .status(400) - .json({ message: "Reorder level cannot be negative" }); - } - - next(); -}; diff --git a/backend/middleware/sub-ware/ticketMiddleware.js b/backend/middleware/sub-ware/ticketMiddleware.js deleted file mode 100644 index f09df616..00000000 --- a/backend/middleware/sub-ware/ticketMiddleware.js +++ /dev/null @@ -1,22 +0,0 @@ -const Ticket = require("../models/Ticket"); - -// Middleware to ensure only the user who created the ticket can update it -const checkTicketOwnership = async (req, res, next) => { - const { ticketId } = req.params; - - const ticket = await Ticket.findOne({ ticketId }); - - if (!ticket) { - return res.status(404).json({ message: "Ticket not found" }); - } - - if (ticket.userId.toString() !== req.user.id) { - return res - .status(403) - .json({ message: "You are not authorized to update this ticket" }); - } - - next(); -}; - -module.exports = { checkTicketOwnership }; diff --git a/backend/middleware/sub-ware/validate.js b/backend/middleware/sub-ware/validate.js deleted file mode 100644 index 792c4a16..00000000 --- a/backend/middleware/sub-ware/validate.js +++ /dev/null @@ -1,15 +0,0 @@ - -const { check, validationResult } = require('express-validator'); - -exports.validateDeliveryPerson = [ - check('email').isEmail().withMessage('Email is invalid'), - check('phone_number').isMobilePhone().withMessage('Phone number is invalid'), - check('status').isIn(['active', 'inactive']).withMessage('Status must be active or inactive'), - (req, res, next) => { - const errors = validationResult(req); - if (!errors.isEmpty()) { - return res.status(400).json({ errors: errors.array() }); - } - next(); - } -]; diff --git a/backend/middleware/sub-ware/validateCoupon.js b/backend/middleware/sub-ware/validateCoupon.js deleted file mode 100644 index 528959ce..00000000 --- a/backend/middleware/sub-ware/validateCoupon.js +++ /dev/null @@ -1,21 +0,0 @@ -const { validateCoupon } = require('../../middleware/sub-ware/validateCoupon'); - -module.exports = async (req, res, next) => { - const { code, orderAmount } = req.body; - try { - const coupon = await Coupon.findOne({ code }); - if (!coupon) { - return res.status(404).json({ error: 'Coupon not found' }); - } - - const isValid = await validateCoupon(coupon, orderAmount); - if (!isValid) { - return res.status(400).json({ error: 'Coupon is invalid' }); - } - - req.coupon = coupon; // Attach coupon to the request object for use in further steps - next(); - } catch (err) { - res.status(500).json({ error: 'Error validating coupon' }); - } -}; diff --git a/backend/middleware/sub-ware/validatePaymentInvoice.js b/backend/middleware/sub-ware/validatePaymentInvoice.js deleted file mode 100644 index e208773e..00000000 --- a/backend/middleware/sub-ware/validatePaymentInvoice.js +++ /dev/null @@ -1,25 +0,0 @@ -const validatePaymentData = (req, res, next) => { - const { orderId, userId, amount, paymentMethod, transactionId } = req.body; - - if (!orderId || !userId || !amount || !paymentMethod || !transactionId) { - return res - .status(400) - .json({ message: "All fields are required for payment" }); - } - - next(); -}; - -const validateInvoiceData = (req, res, next) => { - const { orderId, userId, amount, dueDate, paymentId } = req.body; - - if (!orderId || !userId || !amount || !dueDate || !paymentId) { - return res - .status(400) - .json({ message: "All fields are required for invoice" }); - } - - next(); -}; - -module.exports = { validatePaymentData, validateInvoiceData }; diff --git a/backend/middleware/sub-ware/validationMiddleware.js b/backend/middleware/sub-ware/validationMiddleware.js deleted file mode 100644 index c569037d..00000000 --- a/backend/middleware/sub-ware/validationMiddleware.js +++ /dev/null @@ -1,28 +0,0 @@ -const Joi = require('joi'); - -// Validation schema for supplier data -const supplierValidationSchema = Joi.object({ - name: Joi.string().required(), - contactInfo: Joi.object({ - email: Joi.string().email().required(), - phone: Joi.string().required(), - }).required(), - address: Joi.object({ - street: Joi.string().required(), - city: Joi.string().required(), - state: Joi.string().required(), - postalCode: Joi.string().required(), - }).required(), - productsSupplied: Joi.array().items(Joi.string()).required(), - status: Joi.string().valid('active', 'inactive').default('active'), -}); - -const validateSupplierData = (req, res, next) => { - const { error } = supplierValidationSchema.validate(req.body); - if (error) { - return res.status(400).json({ message: 'Validation Error', details: error.details }); - } - next(); -}; - -module.exports = validateSupplierData; diff --git a/backend/middleware/sub-ware/warehouseMiddleware.js b/backend/middleware/sub-ware/warehouseMiddleware.js deleted file mode 100644 index 6d79ded9..00000000 --- a/backend/middleware/sub-ware/warehouseMiddleware.js +++ /dev/null @@ -1,67 +0,0 @@ -const Warehouse = require("../models/Warehouse"); - -// Middleware to check if warehouse exists by ID -const checkWarehouseExists = async (req, res, next) => { - const { warehouseId } = req.params; - const warehouse = await Warehouse.findOne({ warehouseId }); - if (!warehouse) { - return res.status(404).json({ message: "Warehouse not found" }); - } - req.warehouse = warehouse; - next(); -}; - -// Middleware to validate warehouse fields during updates -const validateWarehouseFields = (req, res, next) => { - const { capacity, currentOccupancy, address } = req.body; - - // Validate capacity - if (capacity <= 0) { - return res - .status(400) - .json({ message: "Capacity must be a positive number" }); - } - - // Validate that currentOccupancy does not exceed capacity - if (currentOccupancy > capacity) { - return res - .status(400) - .json({ message: "Current Occupancy cannot exceed Warehouse Capacity" }); - } - - // Validate address fields - if ( - !address || - !address.street || - !address.city || - !address.state || - !address.zip || - !address.country - ) { - return res.status(400).json({ message: "Address fields must be complete" }); - } - - next(); -}; - -// Middleware to validate unique warehouse ID or name -const validateUniqueWarehouse = async (req, res, next) => { - const { warehouseId, warehouseName } = req.body; - - const existingWarehouse = await Warehouse.findOne({ - $or: [{ warehouseId }, { warehouseName }], - }); - if (existingWarehouse) { - return res - .status(400) - .json({ message: "Warehouse ID or Name must be unique" }); - } - - next(); -}; - -module.exports = { - checkWarehouseExists, - validateWarehouseFields, - validateUniqueWarehouse, -}; diff --git a/backend/model/shop/sub-model/Agent.js b/backend/model/shop/sub-model/Agent.js deleted file mode 100644 index 5c525382..00000000 --- a/backend/model/shop/sub-model/Agent.js +++ /dev/null @@ -1,39 +0,0 @@ -const mongoose = require("mongoose"); - -const agentSchema = new mongoose.Schema({ - name: { - type: String, - required: true, - }, - email: { - type: String, - required: true, - unique: true, - validate: { - validator: (v) => /@/.test(v), // simple email validation - message: (props) => `${props.value} is not a valid email!`, - }, - }, - assigned_tickets: [ - { - type: mongoose.Schema.Types.ObjectId, - ref: "Ticket", - }, - ], - status: { - type: String, - enum: ["active", "inactive"], - default: "active", - }, - role: { - type: String, - enum: ["admin", "support"], - default: "support", - }, - created_at: { - type: Date, - default: Date.now, - }, -}); - -module.exports = mongoose.model("Agent", agentSchema); diff --git a/backend/model/shop/sub-model/DeliveryPerson.js b/backend/model/shop/sub-model/DeliveryPerson.js deleted file mode 100644 index 03d9afe3..00000000 --- a/backend/model/shop/sub-model/DeliveryPerson.js +++ /dev/null @@ -1,44 +0,0 @@ -// models/DeliveryPerson.js -const mongoose = require("mongoose"); - -const deliveryPersonSchema = new mongoose.Schema({ - name: { - type: String, - required: true, - }, - email: { - type: String, - required: true, - unique: true, - }, - phone_number: { - type: String, - required: true, - }, - status: { - type: String, - enum: ["active", "inactive"], - required: true, - }, - assigned_routes: [{ type: mongoose.Schema.Types.ObjectId, ref: "Route" }], - vehicle_details: { - vehicle_type: { type: String }, - vehicle_number: { type: String }, - }, - created_at: { - type: Date, - default: Date.now, - }, - updated_at: { - type: Date, - default: Date.now, - }, - password: { - type: String -}, - profile_picture: { - type: String - }, -}); - -module.exports = mongoose.model("DeliveryPerson", deliveryPersonSchema); diff --git a/backend/model/shop/sub-model/GiftCard.js b/backend/model/shop/sub-model/GiftCard.js deleted file mode 100644 index e0c713bb..00000000 --- a/backend/model/shop/sub-model/GiftCard.js +++ /dev/null @@ -1,37 +0,0 @@ - -const mongoose = require('mongoose'); - -const giftCardSchema = new mongoose.Schema({ - cardNumber: { - type: String, - required: true, - unique: true, - }, - value: { - type: Number, - required: true, - min: 0.01, - }, - status: { - type: String, - enum: ['active', 'redeemed', 'expired'], - default: 'active', - }, - userId: { - type: mongoose.Schema.Types.ObjectId, - ref: 'User', - required: true, - }, - expiryDate: { - type: Date, - required: true, - }, - createdAt: { - type: Date, - default: Date.now, - }, -}); - -const GiftCard = mongoose.model('GiftCard', giftCardSchema); - -module.exports = GiftCard; diff --git a/backend/model/shop/sub-model/InventoryModel.js b/backend/model/shop/sub-model/InventoryModel.js deleted file mode 100644 index 734e6c13..00000000 --- a/backend/model/shop/sub-model/InventoryModel.js +++ /dev/null @@ -1,57 +0,0 @@ -const mongoose = require('mongoose'); - -const inventorySchema = new mongoose.Schema({ - productId: { - type: mongoose.Schema.Types.ObjectId, - ref: 'Product', // Reference to the Product collection - required: true - }, - currentStockLevel: { - type: Number, - required: true, - min: 0 // Stock can't be negative - }, - reorderLevel: { - type: Number, - required: true, - min: 0 // Threshold can't be negative - }, - lastRestockedDate: { - type: Date, - default: Date.now - }, - supplierId: { - type: mongoose.Schema.Types.ObjectId, - ref: 'Supplier', // Optional link to Supplier schema - }, - warehouseLocation: { - type: String, - required: true // Warehouse location field - }, - reorderNotificationSent: { - type: Boolean, - default: false // Indicates if a reorder alert has been triggered - }, - auditLog: [{ - action: String, // Describes the action (e.g., "Stock Update", "Reorder Triggered") - actionDate: { - type: Date, - default: Date.now - }, - performedBy: String, // User who performed the action - quantityChanged: Number, // Amount of stock changed - notes: String // Additional details about the action - }], - lastCheckedDate: { - type: Date, - default: Date.now // Timestamp for the last reorder level check - } -}); - -// Virtual to get the last audit entry -inventorySchema.virtual('latestAuditEntry').get(function () { - return this.auditLog.length > 0 ? this.auditLog[this.auditLog.length - 1] : null; -}); - -const Inventory = mongoose.model('Inventory', inventorySchema); -module.exports = Inventory; diff --git a/backend/model/shop/sub-model/OrderHistory.js b/backend/model/shop/sub-model/OrderHistory.js deleted file mode 100644 index dffbfab0..00000000 --- a/backend/model/shop/sub-model/OrderHistory.js +++ /dev/null @@ -1,43 +0,0 @@ -const mongoose = require("mongoose"); - - -const OrderHistorySchema = new mongoose.Schema( - { - userId: { - type: mongoose.Schema.Types.ObjectId, - ref: "User", - required: true, - }, - orderDate: { type: Date, default: Date.now }, - orderStatus: { - type: String, - enum: ["Pending", "Shipped", "Delivered"], - default: "Pending", - }, - totalAmount: { type: Number, required: true }, - shippingAddress: { type: String, required: true }, - paymentStatus: { - type: String, - enum: ["Paid", "Pending"], - default: "Pending", - }, - items: [ - { - productId: { - type: mongoose.Schema.Types.ObjectId, - ref: "Product", - required: true, - }, - quantity: { type: Number, required: true }, - pricePerUnit: { type: Number, required: true }, - }, - ], - trackingNumber: { type: String, optional: true }, - }, - { timestamps: true } -); - -const OrderHistory = mongoose.model("OrderHistory", OrderHistorySchema); - -module.exports = OrderHistory; - diff --git a/backend/model/shop/sub-model/OrderTracking.js b/backend/model/shop/sub-model/OrderTracking.js deleted file mode 100644 index 52c5e585..00000000 --- a/backend/model/shop/sub-model/OrderTracking.js +++ /dev/null @@ -1,83 +0,0 @@ -const mongoose = require("mongoose"); - -const Schema = mongoose.Schema; - -const OrderTrackingSchema = new Schema({ - orderId: { - type: Schema.Types.ObjectId, - ref: "OrderHistory", - required: true, - }, - trackingNumber: { - type: String, - required: true, - }, - status: { - type: String, - enum: ["Pending", "Shipped", "Delivered"], - required: true, - }, - carrier: { - type: String, - required: true, - }, - estimatedDelivery: { - type: Date, - }, - updatedAt: { - type: Date, - default: Date.now, - }, -}); - -// Schema Methods - -// Update the status of the order and update the updatedAt timestamp -OrderTrackingSchema.methods.updateStatus = function(newStatus) { - this.status = newStatus; - this.updatedAt = Date.now(); - return this.save(); -}; - -// Check if the order is overdue based on the estimated delivery date -OrderTrackingSchema.methods.isOverdue = function() { - if (this.estimatedDelivery && this.status !== "Delivered") { - const today = new Date(); - return today > this.estimatedDelivery; - } - return false; -}; - -// Format estimated delivery date in a user-friendly format (e.g., MM/DD/YYYY) -OrderTrackingSchema.methods.formatEstimatedDelivery = function() { - if (!this.estimatedDelivery) return "N/A"; - const options = { year: 'numeric', month: 'short', day: 'numeric' }; - return this.estimatedDelivery.toLocaleDateString(undefined, options); -}; - -// Schema Statics - -// Find orders by status -OrderTrackingSchema.statics.findByStatus = function(status) { - return this.find({ status }); -}; - -// Find all overdue orders -OrderTrackingSchema.statics.findOverdueOrders = function() { - const today = new Date(); - return this.find({ - estimatedDelivery: { $lt: today }, - status: { $ne: "Delivered" }, - }); -}; - -// Bulk update status for multiple orders by order IDs -OrderTrackingSchema.statics.bulkUpdateStatus = function(orderIds, newStatus) { - return this.updateMany( - { orderId: { $in: orderIds } }, - { status: newStatus, updatedAt: Date.now() } - ); -}; - -// Export the model -module.exports = mongoose.model("OrderTracking", OrderTrackingSchema); diff --git a/backend/model/shop/sub-model/Referral.js b/backend/model/shop/sub-model/Referral.js deleted file mode 100644 index 3f05b8ea..00000000 --- a/backend/model/shop/sub-model/Referral.js +++ /dev/null @@ -1,32 +0,0 @@ - -const mongoose = require("mongoose"); -const { Schema } = mongoose; - -const referralSchema = new Schema({ - referrerId: { - type: Schema.Types.ObjectId, - ref: "User", - required: true, - }, - refereeId: { - type: Schema.Types.ObjectId, - ref: "User", - required: false, - }, - referralCode: { - type: String, - required: true, - unique: true, - }, - status: { - type: String, - enum: ["pending", "completed"], - default: "pending", - }, - timestamp: { - type: Date, - default: Date.now, - }, -}); - -module.exports = mongoose.model("Referral", referralSchema); diff --git a/backend/model/shop/sub-model/ReturnProduct.js b/backend/model/shop/sub-model/ReturnProduct.js deleted file mode 100644 index 9a5b7023..00000000 --- a/backend/model/shop/sub-model/ReturnProduct.js +++ /dev/null @@ -1,42 +0,0 @@ - -const mongoose = require('mongoose'); - -const returnProductSchema = new mongoose.Schema( - { - productId: { - type: mongoose.Schema.Types.ObjectId, - ref: 'Product', - required: true - }, - userId: { - type: mongoose.Schema.Types.ObjectId, - ref: 'User', - required: true - }, - returnDate: { - type: Date, - required: true - }, - condition: { - type: String, - enum: ['good', 'damaged'], - required: true - }, - status: { - type: String, - enum: ['pending', 'returned', 'approved', 'rejected'], - default: 'pending' - }, - createdAt: { - type: Date, - default: Date.now - }, - updatedAt: { - type: Date, - default: Date.now - } - }, - { timestamps: true } -); - -module.exports = mongoose.model('ReturnProduct', returnProductSchema); diff --git a/backend/model/shop/sub-model/ShippingAddress.js b/backend/model/shop/sub-model/ShippingAddress.js deleted file mode 100644 index 9cdf9858..00000000 --- a/backend/model/shop/sub-model/ShippingAddress.js +++ /dev/null @@ -1,37 +0,0 @@ - -const mongoose = require('mongoose'); -const Schema = mongoose.Schema; - -const ShippingAddressSchema = new Schema({ - addressLine1: { - type: String, - required: true - }, - addressLine2: { - type: String, - required: false - }, - city: { - type: String, - required: true - }, - state: { - type: String, - required: true - }, - postalCode: { - type: String, - required: true - }, - country: { - type: String, - required: true - }, - user: { - type: mongoose.Schema.Types.ObjectId, - ref: 'User', // assuming a 'User' model exists for users - required: true - } -}, { timestamps: true }); - -module.exports = mongoose.model('ShippingAddress', ShippingAddressSchema); diff --git a/backend/model/shop/sub-model/Supplier.js b/backend/model/shop/sub-model/Supplier.js deleted file mode 100644 index 7d466d78..00000000 --- a/backend/model/shop/sub-model/Supplier.js +++ /dev/null @@ -1,58 +0,0 @@ -const mongoose = require("mongoose"); - -const supplierSchema = new mongoose.Schema( - { - name: { - type: String, - required: true, - }, - contactInfo: { - email: { - type: String, - required: true, - unique: true, - }, - phone: { - type: String, - required: true, - }, - }, - address: { - street: { - type: String, - required: true, - }, - city: { - type: String, - required: true, - }, - state: { - type: String, - required: true, - }, - postalCode: { - type: String, - required: true, - }, - }, - productsSupplied: [ - { type: mongoose.Schema.Types.ObjectId, ref: "Product" }, - ], - status: { - type: String, - required: true, - default: "active", - }, - createdAt: { - type: Date, - default: Date.now, - }, - updatedAt: { - type: Date, - default: Date.now, - }, - }, - { timestamps: true } -); - -module.exports = mongoose.model("Supplier", supplierSchema); diff --git a/backend/model/shop/sub-model/TIcket.js b/backend/model/shop/sub-model/TIcket.js deleted file mode 100644 index 53af2a83..00000000 --- a/backend/model/shop/sub-model/TIcket.js +++ /dev/null @@ -1,46 +0,0 @@ -const mongoose = require("mongoose"); - -const ticketSchema = new mongoose.Schema({ - ticketId: { - type: String, - required: true, - unique: true, - }, - userId: { - type: mongoose.Schema.Types.ObjectId, - ref: "User", - required: true, - }, - subject: { - type: String, - required: true, - }, - description: { - type: String, - required: true, - }, - status: { - type: String, - enum: ["open", "in-progress", "resolved"], - default: "open", - }, - priority: { - type: String, - enum: ["low", "medium", "high"], - default: "medium", - }, - assignedAgentId: { - type: mongoose.Schema.Types.ObjectId, - ref: "Agent", - }, - createdAt: { - type: Date, - default: Date.now, - }, - updatedAt: { - type: Date, - default: Date.now, - }, -}); - -module.exports = mongoose.model("Ticket", ticketSchema); diff --git a/backend/model/shop/sub-model/Warehouse.js b/backend/model/shop/sub-model/Warehouse.js deleted file mode 100644 index e691f85a..00000000 --- a/backend/model/shop/sub-model/Warehouse.js +++ /dev/null @@ -1,63 +0,0 @@ -const mongoose = require("mongoose"); - -const warehouseSchema = new mongoose.Schema({ - warehouseId: { - type: String, - unique: true, - required: true - }, - warehouseName: { - type: String, - unique: true, - required: true }, - address: { - street: { - type: String, - required: true - }, - city: { - type: String - , required: true - }, - state: { - type: String, - required: true - }, - zip: { - type: String, - required: true - }, - country: { - type: String, - required: true - }, - }, - capacity: { - type: Number, - required: true - }, - currentOccupancy: { - type: Number, - default: 0 - }, - inventoryItems: [ - { - type: mongoose.Schema.Types.ObjectId, - ref: "InventoryItem" -}, - ], - contactInfo: { - phone: { - type: String - }, - email: { - type: String - }, - }, - lastUpdated: { - type: Date, - default: Date.now - }, -}); - -module.exports = mongoose.model("Warehouse", warehouseSchema); diff --git a/backend/model/shop/sub-model/couponModel.js b/backend/model/shop/sub-model/couponModel.js deleted file mode 100644 index e873895f..00000000 --- a/backend/model/shop/sub-model/couponModel.js +++ /dev/null @@ -1,61 +0,0 @@ -const mongoose = require("mongoose"); - -const couponSchema = new mongoose.Schema({ - code: { - type: String, - unique: true, - required: true - }, - description: { - type: String, - required: true - }, - discountType: { - type: String, - enum: ["percentage", "fixed"], - required: true - }, - discountValue: { - type: Number, - required: true - }, - minOrderAmount: { - type: Number, - default: 0 - }, - maxDiscount: { - type: Number, - default: 0 - }, - startDate: { - type: Date, - required: true - }, - endDate: { - type: Date, - required: true - }, - status: { - type: String, - enum: ["active", "inactive"], - default: "active" - }, - usageLimit: { - type: Number, - required: true - }, - usageCount: { - type: Number, - default: 0 - }, - createdAt: { - type: Date, - default: Date.now - }, - updatedAt: { - type: Date, - default: Date.now - } -}); - -module.exports = mongoose.model("Coupon", couponSchema); diff --git a/backend/model/shop/sub-model/damagemodal.js b/backend/model/shop/sub-model/damagemodal.js deleted file mode 100644 index 815e8e56..00000000 --- a/backend/model/shop/sub-model/damagemodal.js +++ /dev/null @@ -1,27 +0,0 @@ -const mongoose = require('mongoose'); - -const malfunctioningProductSchema = new mongoose.Schema({ - productId: { type: mongoose.Schema.Types.ObjectId, ref: 'Product', required: true }, - description: { type: String, required: true }, - status: { type: String, enum: ['pending', 'in progress', 'resolved'], default: 'pending' }, - reportedDate: { type: Date, default: Date.now }, - resolvedDate: { type: Date }, - actionsTaken: { type: String }, - createdBy: { type: mongoose.Schema.Types.ObjectId, ref: 'User', required: true } -}); - -module.exports = mongoose.model('MalfunctioningProduct', malfunctioningProductSchema); - - - -const damagedProductSchema = new mongoose.Schema({ - productId: { type: mongoose.Schema.Types.ObjectId, ref: 'Product', required: true }, - damageType: { type: String, enum: ['crack', 'scratches', 'water damage', 'other'], required: true }, - damageDescription: { type: String, required: true }, - damageSeverity: { type: String, enum: ['minor', 'moderate', 'severe'], required: true }, - reportedDate: { type: Date, default: Date.now }, - status: { type: String, enum: ['reported', 'under review', 'resolved'], default: 'reported' }, - createdBy: { type: mongoose.Schema.Types.ObjectId, ref: 'User', required: true } -}); - -module.exports = mongoose.model('DamagedProduct', damagedProductSchema); diff --git a/backend/model/shop/sub-model/invoice.js b/backend/model/shop/sub-model/invoice.js deleted file mode 100644 index 5ea2f010..00000000 --- a/backend/model/shop/sub-model/invoice.js +++ /dev/null @@ -1,47 +0,0 @@ -const mongoose = require("mongoose"); - - -const invoiceSchema = new mongoose.Schema( - { - invoiceId: { type: String, required: true, unique: true }, - orderId: { - type: mongoose.Schema.Types.ObjectId, - ref: "Order", - required: true, - }, - userId: { - type: mongoose.Schema.Types.ObjectId, - ref: "User", - required: true, - index: true, // Adds index for faster query on user invoices - }, - amount: { type: Number, required: true, min: 0 }, - invoiceDate: { type: Date, default: Date.now }, - dueDate: { - type: Date, - required: true, - default: function () { - return new Date(+new Date() + 7 * 24 * 60 * 60 * 1000); // Default due date is 7 days from invoice date - }, - }, - status: { - type: String, - enum: ["Paid", "Unpaid", "Overdue", "Cancelled"], - default: "Unpaid", - }, - paymentId: { - type: mongoose.Schema.Types.ObjectId, - ref: "Payment", - sparse: true, // Allows null value indexing for unpaid invoices - }, - }, - { timestamps: true } -); - -// Virtual field to check if invoice is overdue -invoiceSchema.virtual("isOverdue").get(function () { - return this.status === "Unpaid" && this.dueDate < new Date(); -}); - -const Invoice = mongoose.model("Invoice", invoiceSchema); -module.exports = Invoice; diff --git a/backend/model/shop/sub-model/loyaltyPointModel.js b/backend/model/shop/sub-model/loyaltyPointModel.js deleted file mode 100644 index 44cfec6e..00000000 --- a/backend/model/shop/sub-model/loyaltyPointModel.js +++ /dev/null @@ -1,25 +0,0 @@ -const mongoose = require("mongoose"); - -const loyaltyPointSchema = new mongoose.Schema({ - userId: { - type: mongoose.Schema.Types.ObjectId, - required: true, - ref: "User", - }, - points: { - type: Number, - required: true, - default: 0, - }, - earnedBy: { - type: String, - enum: ["purchase", "referral"], - required: true, - }, - timestamp: { - type: Date, - default: Date.now, - }, -}); - -module.exports = mongoose.model("LoyaltyPoint", loyaltyPointSchema); diff --git a/backend/model/shop/sub-model/payment.js b/backend/model/shop/sub-model/payment.js deleted file mode 100644 index 44182dd7..00000000 --- a/backend/model/shop/sub-model/payment.js +++ /dev/null @@ -1,34 +0,0 @@ -const mongoose = require("mongoose"); - -const paymentSchema = new mongoose.Schema( - { - paymentId: { type: String, required: true, unique: true }, - orderId: { - type: mongoose.Schema.Types.ObjectId, - ref: "Order", - required: true, - }, - userId: { - type: mongoose.Schema.Types.ObjectId, - ref: "User", - required: true, - }, - amount: { type: Number, required: true }, - paymentMethod: { - type: String, - enum: ["Credit Card", "PayPal", "Bank Transfer"], - required: true, - }, - paymentStatus: { - type: String, - default: "Pending", - enum: ["Pending", "Completed", "Failed"], - }, - paymentDate: { type: Date, default: Date.now }, - transactionId: { type: String, required: true }, - }, - { timestamps: true } -); - -const Payment = mongoose.model("Payment", paymentSchema); -module.exports = Payment; diff --git a/backend/model/shop/sub-model/productanalysis.jsx b/backend/model/shop/sub-model/productanalysis.jsx deleted file mode 100644 index a106cec4..00000000 --- a/backend/model/shop/sub-model/productanalysis.jsx +++ /dev/null @@ -1,29 +0,0 @@ -const mongoose = require('mongoose'); - -const productAnalysisSchema = new mongoose.Schema({ - productId: { - type: mongoose.Schema.Types.ObjectId, - ref: 'Product', - required: true, - }, - views: { - type: Number, - default: 0, - }, - sales: { - type: Number, - default: 0, - }, - ratings: { - type: Number, - default: 0, - }, - feedback: { - type: [String], - default: [], - }, -}); - -const ProductAnalysis = mongoose.model('ProductAnalysis', productAnalysisSchema); - -module.exports = ProductAnalysis; diff --git a/backend/model/shop/sub-model/useranalysis.js b/backend/model/shop/sub-model/useranalysis.js deleted file mode 100644 index a9779a7e..00000000 --- a/backend/model/shop/sub-model/useranalysis.js +++ /dev/null @@ -1,25 +0,0 @@ -const mongoose = require('mongoose'); - -const userAnalysisSchema = new mongoose.Schema({ - userId: { - type: mongoose.Schema.Types.ObjectId, - ref: 'User', - required: true, - }, - activityLog: { - type: [String], - default: [], - }, - interactions: { - type: Number, - default: 0, - }, - preferences: { - type: Object, - default: {}, - }, -}); - -const UserAnalysis = mongoose.model('UserAnalysis', userAnalysisSchema); - -module.exports = UserAnalysis; diff --git a/backend/model/shop/sub-model/useranalysiscontroller.js b/backend/model/shop/sub-model/useranalysiscontroller.js deleted file mode 100644 index 620ead7b..00000000 --- a/backend/model/shop/sub-model/useranalysiscontroller.js +++ /dev/null @@ -1,172 +0,0 @@ -const UserAnalysis = require("../models/UserAnalysis"); -const mongoose = require("mongoose"); - -// Utility function to validate ObjectId -const isValidObjectId = (id) => mongoose.Types.ObjectId.isValid(id); - -// Create User Analysis -exports.createUserAnalysis = async (req, res) => { - try { - const { userId, activityLog, interactions, preferences } = req.body; - - // Input validation - if ( - !userId || - !activityLog || - !Array.isArray(activityLog) || - !interactions || - !preferences - ) { - return res - .status(400) - .json({ - message: - "Missing required fields: userId, activityLog, interactions, preferences", - }); - } - - // Check if the userId is valid - if (!isValidObjectId(userId)) { - return res.status(400).json({ message: "Invalid userId format" }); - } - - // Create new UserAnalysis record - const userAnalysis = new UserAnalysis({ - userId, - activityLog, - interactions, - preferences, - }); - await userAnalysis.save(); - res.status(201).json(userAnalysis); - } catch (error) { - console.error(error); // For debugging purposes - if (error.code === 11000) { - return res - .status(409) - .json({ message: "Duplicate entry detected for user analysis" }); - } - res - .status(500) - .json({ message: "Error creating user analysis data", error }); - } -}; - -// Get User Analysis by ID -exports.getUserAnalysis = async (req, res) => { - try { - const { id } = req.params; - - // Check if the id is a valid ObjectId - if (!isValidObjectId(id)) { - return res - .status(400) - .json({ message: "Invalid UserAnalysis ID format" }); - } - - const userAnalysis = await UserAnalysis.findById(id); - - if (!userAnalysis) { - return res.status(404).json({ message: "User analysis not found" }); - } - - res.status(200).json(userAnalysis); - } catch (error) { - console.error(error); // For debugging purposes - res - .status(500) - .json({ message: "Error retrieving user analysis data", error }); - } -}; - -// Update User Analysis by ID -exports.updateUserAnalysis = async (req, res) => { - try { - const { id } = req.params; - const updatedData = req.body; - - // Check if the id is a valid ObjectId - if (!isValidObjectId(id)) { - return res - .status(400) - .json({ message: "Invalid UserAnalysis ID format" }); - } - - // Input validation: Ensure there is at least one field to update - if (!updatedData || Object.keys(updatedData).length === 0) { - return res.status(400).json({ message: "No data provided to update" }); - } - - // Check for fields that shouldn't be updated or are invalid - if (updatedData.userId && !isValidObjectId(updatedData.userId)) { - return res.status(400).json({ message: "Invalid userId format" }); - } - - const userAnalysis = await UserAnalysis.findByIdAndUpdate(id, updatedData, { - new: true, - }); - - if (!userAnalysis) { - return res.status(404).json({ message: "User analysis not found" }); - } - - res.status(200).json(userAnalysis); - } catch (error) { - console.error(error); // For debugging purposes - if (error.code === 11000) { - return res - .status(409) - .json({ message: "Duplicate entry detected during update" }); - } - res - .status(500) - .json({ message: "Error updating user analysis data", error }); - } -}; - -// Delete User Analysis by ID (Optional - In case we want to support deleting analysis data) -exports.deleteUserAnalysis = async (req, res) => { - try { - const { id } = req.params; - - // Check if the id is a valid ObjectId - if (!isValidObjectId(id)) { - return res - .status(400) - .json({ message: "Invalid UserAnalysis ID format" }); - } - - const userAnalysis = await UserAnalysis.findByIdAndDelete(id); - - if (!userAnalysis) { - return res.status(404).json({ message: "User analysis not found" }); - } - - res.status(200).json({ message: "User analysis deleted successfully" }); - } catch (error) { - console.error(error); // For debugging purposes - res - .status(500) - .json({ message: "Error deleting user analysis data", error }); - } -}; - -// Get all User Analysis records (Optional - If we want to list all data) -exports.getAllUserAnalysis = async (req, res) => { - try { - const userAnalysis = await UserAnalysis.find(); - - if (userAnalysis.length === 0) { - return res - .status(404) - .json({ message: "No user analysis data available" }); - } - - res.status(200).json(userAnalysis); - } catch (error) { - console.error(error); // For debugging purposes - res - .status(500) - .json({ message: "Error retrieving all user analysis data", error }); - } -}; diff --git a/backend/routes/sub-routes/agentRoutes.js b/backend/routes/sub-routes/agentRoutes.js deleted file mode 100644 index 28067322..00000000 --- a/backend/routes/sub-routes/agentRoutes.js +++ /dev/null @@ -1,39 +0,0 @@ -const express = require('express'); -const router = express.Router(); -const agentController = require('../../controllers/shop/sub-controllers/agentController'); -const { checkAgentRole } = require('../../middleware/sub-ware/agentMiddleware'); - -// Routes for Agent management - -// Get all agents -router.get('/agents', agentController.getAllAgents); - -// Create a new agent -router.post('/agents', agentController.createAgent); - -// Get agent by ID -router.get('/agents/:id', agentController.getAgentById); - -// Update agent details by ID -router.put('/agents/:id', agentController.updateAgent); - -// Delete agent by ID -router.delete('/agents/:id', agentController.deleteAgent); - -// Assign a ticket to an agent -router.patch('/agents/:id/assign-ticket', agentController.assignTicketToAgent); - -// Unassign a ticket from an agent -router.patch('/agents/:id/unassign-ticket', agentController.unassignTicketFromAgent); - -// Change the status of an agent (active/inactive) -router.patch('/agents/:id/status', agentController.changeAgentStatus); - -// Assign multiple tickets to an agent -router.patch('/agents/:id/assign-multiple-tickets', agentController.assignMultipleTickets); - -// Role-based access check for certain admin actions -router.use('/agents/:id', checkAgentRole); - -// Export the router -module.exports = router; diff --git a/backend/routes/sub-routes/couponRoutes.js b/backend/routes/sub-routes/couponRoutes.js deleted file mode 100644 index 1c62e3b0..00000000 --- a/backend/routes/sub-routes/couponRoutes.js +++ /dev/null @@ -1,34 +0,0 @@ -const express = require('express'); -const router = express.Router(); -const couponController = require('../../controllers/shop/sub-controllers/couponController'); - -// Route to create a new coupon -router.post('/create', couponController.createCoupon); - -// Route to fetch all coupons -router.get('/', couponController.getCoupons); - -// Route to get a specific coupon by its code -router.get('/:code', couponController.getCouponByCode); - -// Route to update a coupon -router.put('/:code', couponController.updateCoupon); - -// Route to delete a coupon -router.delete('/:code', couponController.deleteCoupon); - -// Route to validate a coupon before applying to an order -router.post('/validate', couponController.validateCoupon, (req, res) => { - res.status(200).json({ message: 'Coupon is valid', coupon: req.coupon }); -}); - -// Route to track coupon usage -router.post('/usage', couponController.incrementUsageCount); - -// Route to activate or deactivate a coupon -router.put('/:code/status', couponController.toggleCouponStatus); - -// Route to apply coupon to an order -router.post('/apply', couponController.applyCouponToOrder); - -module.exports = router; diff --git a/backend/routes/sub-routes/giftCardRoutes.js b/backend/routes/sub-routes/giftCardRoutes.js deleted file mode 100644 index 817e403f..00000000 --- a/backend/routes/sub-routes/giftCardRoutes.js +++ /dev/null @@ -1,38 +0,0 @@ - -const express = require('express'); -const router = express.Router(); - -// Import the GiftCard Controller -const GiftCardController = require('../../controllers/shop/sub-controllers/giftCardController'); - -// Middleware to validate gift cards (to check status, expiry, etc.) -const validateGiftCard = require('../../middleware/sub-ware/giftCardMiddleware'); - -// Route to create a new gift card -router.post('/api/gift-cards', GiftCardController.createGiftCard); - -// Route to get details of a specific gift card by card number -router.get('/api/gift-cards/:cardNumber', GiftCardController.getGiftCardDetails); - -// Route to redeem a gift card by card number -router.post('/api/gift-cards/redeem', validateGiftCard, GiftCardController.redeemGiftCard); - -// Route to fetch all gift cards for a user (e.g., list of user's gift cards) -router.get('/api/gift-cards/user/:userId', GiftCardController.getUserGiftCards); - -// Route to search gift cards within a specific value range -router.get('/api/gift-cards/search', GiftCardController.searchGiftCardsByValue); - -// Route to delete a gift card (forceful deletion) -router.delete('/api/gift-cards/:cardNumber', GiftCardController.deleteGiftCard); - -// Route to deactivate (expire) a gift card before redemption -router.patch('/api/gift-cards/deactivate/:cardNumber', GiftCardController.deactivateGiftCard); - -// Route to fetch all gift cards (Admin-only route) -router.get('/api/gift-cards', GiftCardController.getAllGiftCards); - -// Route to get statistics on redeemed gift cards -router.get('/api/gift-cards/stats', GiftCardController.getGiftCardStats); - -module.exports = router; diff --git a/backend/routes/sub-routes/invoiceRoutes.js b/backend/routes/sub-routes/invoiceRoutes.js deleted file mode 100644 index a6f30c3d..00000000 --- a/backend/routes/sub-routes/invoiceRoutes.js +++ /dev/null @@ -1,39 +0,0 @@ -const express = require("express"); -const router = express.Router(); - -const { - generateInvoice, - getInvoices, - getInvoiceById, - updateInvoiceStatus, - deleteInvoice, - markOverdueInvoices, - invoiceSummary, - generateBulkInvoices, -} = require("../controllers/invoiceController"); - -// Route to generate a new invoice after payment confirmation -router.post("/generate", generateInvoice); - -// Route to retrieve invoices by user, order, status, or date range with pagination and sorting -router.get("/", getInvoices); - -// Route to retrieve a specific invoice by its ID -router.get("/:id", getInvoiceById); - -// Route to update an invoice's status -router.patch("/:id/status", updateInvoiceStatus); - -// Route to delete an invoice by its ID -router.delete("/:id", deleteInvoice); - -// Route to mark overdue invoices (based on the current date) -router.patch("/mark-overdue", markOverdueInvoices); - -// Route to get an invoice summary (by status, optionally by user) -router.get("/summary", invoiceSummary); - -// Route to generate bulk invoices at once -router.post("/generate-bulk", generateBulkInvoices); - -module.exports = router; diff --git a/backend/routes/sub-routes/loyaltyPointsRoutes.js b/backend/routes/sub-routes/loyaltyPointsRoutes.js deleted file mode 100644 index f8dd54fd..00000000 --- a/backend/routes/sub-routes/loyaltyPointsRoutes.js +++ /dev/null @@ -1,77 +0,0 @@ -const express = require("express"); -const loyaltyPointsController = require("../../controllers/shop/sub-controllers/loyaltyPointsController"); -const authMiddleware = require("../middleware/authMiddleware"); // Middleware to check valid user - -const router = express.Router(); - -// Route to award points to a user -router.post( - "/api/loyalty-points", - authMiddleware, - loyaltyPointsController.awardPoints -); - -// Route to get a user's total loyalty points -router.get( - "/api/loyalty-points/:userId", - authMiddleware, - loyaltyPointsController.getPoints -); - -// Route to get a user's transaction history of loyalty points -router.get( - "/api/loyalty-points/:userId/history", - authMiddleware, - loyaltyPointsController.getTransactionHistory -); - -// Route to delete a specific loyalty points transaction -router.delete( - "/api/loyalty-points/:transactionId", - authMiddleware, - loyaltyPointsController.deletePoints -); - -// Route to update a specific loyalty points transaction -router.put( - "/api/loyalty-points/:transactionId", - authMiddleware, - loyaltyPointsController.updatePoints -); - -// Route to filter transactions by type (e.g., 'purchase', 'referral') -router.get( - "/api/loyalty-points/:userId/filter", - authMiddleware, - loyaltyPointsController.filterTransactionsByType -); - -// Route to get total points earned through referrals -router.get( - "/api/loyalty-points/:userId/referrals", - authMiddleware, - loyaltyPointsController.getPointsByReferrals -); - -// Route to get total points earned through purchases -router.get( - "/api/loyalty-points/:userId/purchases", - authMiddleware, - loyaltyPointsController.getPointsByPurchases -); - -// Route to redeem points -router.post( - "/api/loyalty-points/redeem", - authMiddleware, - loyaltyPointsController.redeemPoints -); - -// Route to get loyalty points summary (overall points, referral points, and purchase points) -router.get( - "/api/loyalty-points/:userId/summary", - authMiddleware, - loyaltyPointsController.getLoyaltySummary -); - -module.exports = router; diff --git a/backend/routes/sub-routes/paymentRoutes.js b/backend/routes/sub-routes/paymentRoutes.js deleted file mode 100644 index 47c456df..00000000 --- a/backend/routes/sub-routes/paymentRoutes.js +++ /dev/null @@ -1,34 +0,0 @@ -const express = require("express"); -const router = express.Router(); -const { - getAllPayments, - getPaymentById, - getPaymentsByUserId, - getPaymentsByStatus, - createPayment, - updatePaymentStatus, - deletePayment, - updatePaymentMethod, - getPaymentsByDateRange, - getPaymentsByAmountRange, - getPaymentByTransactionId, - countPaymentsByStatus, -} = require("../controllers/paymentController"); - -// Payment routes -router.get("/", getAllPayments); // Retrieve all payments -router.get("/:id", getPaymentById); // Retrieve payment by ID -router.get("/user/:userId", getPaymentsByUserId); // Retrieve payments by User ID -router.get("/status/:status", getPaymentsByStatus); // Retrieve payments by Status -router.post("/", createPayment); // Create a new payment -router.patch("/:id/status", updatePaymentStatus); // Update payment status -router.patch("/:id/method", updatePaymentMethod); // Update payment method -router.delete("/:id", deletePayment); // Delete payment - -// Additional routes for edge cases -router.get("/date-range", getPaymentsByDateRange); // Retrieve payments by date range -router.get("/amount-range", getPaymentsByAmountRange); // Retrieve payments by amount range -router.get("/transaction/:transactionId", getPaymentByTransactionId); // Retrieve payment by transaction ID -router.get("/count/status", countPaymentsByStatus); // Count payments by status - -module.exports = router; diff --git a/backend/routes/sub-routes/referralRoutes.js b/backend/routes/sub-routes/referralRoutes.js deleted file mode 100644 index ea7b5096..00000000 --- a/backend/routes/sub-routes/referralRoutes.js +++ /dev/null @@ -1,35 +0,0 @@ -const express = require("express"); -const router = express.Router(); -const referralController = require("../controllers/referralController"); - -// Route to create a new referral -// Endpoint: POST /api/referrals -router.post("/", - referralController.createReferral); - -// Route to check referral status by code -// Endpoint: GET /api/referrals/status/:code -router.get("/status/:code", - referralController.checkReferralStatus); - -// Route to complete a referral when a referral code is used by a referee -// Endpoint: POST /api/referrals/complete -router.post("/complete", - referralController.completeReferral); - -// Route to get all referrals by a specific referrer, with optional status filter and pagination -// Endpoint: GET /api/referrals/referrer/:referrerId -router.get("/referrer/:referrerId", - referralController.getReferralsByReferrer); - -// Route for admin to list all referrals with pagination and sorting -// Endpoint: GET /api/referrals -router.get("/", - referralController.listAllReferrals); - -// Route to cancel a pending referral by code -// Endpoint: POST /api/referrals/cancel -router.post("/cancel", - referralController.cancelReferral); - -module.exports = router; diff --git a/backend/routes/sub-routes/returnRoutes.js b/backend/routes/sub-routes/returnRoutes.js deleted file mode 100644 index e7a32ccc..00000000 --- a/backend/routes/sub-routes/returnRoutes.js +++ /dev/null @@ -1,33 +0,0 @@ -const express = require('express'); -const router = express.Router(); -const { createReturn, updateReturnStatus, getReturnInformation, getUserReturnHistory, getPendingReturns, cancelReturnRequest, getAllReturnedProducts, getAllDamagedProducts, getReturnRequestsForProduct } = require('../../controllers/shop/sub-controllers/returnController'); -const { authenticateUser, authorizeAdmin } = require('../middleware/auth'); - -// Route to create a return request -router.post('/returns', authenticateUser, createReturn); - -// Route to update return status (Admin only) -router.patch('/returns/:id', authenticateUser, authorizeAdmin, updateReturnStatus); - -// Route to get return information -router.get('/returns/:id', authenticateUser, getReturnInformation); - -// Route to get a user's return history -router.get('/returns/user/:userId', authenticateUser, getUserReturnHistory); - -// Route to get all pending returns (Admin only) -router.get('/returns/pending', authenticateUser, authorizeAdmin, getPendingReturns); - -// Route to cancel return request -router.patch('/returns/cancel/:id', authenticateUser, cancelReturnRequest); - -// Route to get all returned products (Admin only) -router.get('/returns/returned', authenticateUser, authorizeAdmin, getAllReturnedProducts); - -// Route to get all damaged products (Admin only) -router.get('/returns/damaged', authenticateUser, authorizeAdmin, getAllDamagedProducts); - -// Route to get return requests for a specific product (Admin only) -router.get('/returns/product/:productId', authenticateUser, authorizeAdmin, getReturnRequestsForProduct); - -module.exports = router; diff --git a/backend/routes/sub-routes/routesdamage b/backend/routes/sub-routes/routesdamage deleted file mode 100644 index 0b829c77..00000000 --- a/backend/routes/sub-routes/routesdamage +++ /dev/null @@ -1,54 +0,0 @@ -const express = require("express"); -const router = express.Router(); -const MalfunctioningProductController = require("../controllers/MalfunctioningProductController"); -const { - validateMalfunctioningProduct, - validateUpdateMalfunctioningProduct, -} = require("../middlewares/validationMiddleware"); -const authenticate = require("../middlewares/authenticationMiddleware"); - -// Create malfunctioning product -router.post( - "/", - authenticate, - validateMalfunctioningProduct, - MalfunctioningProductController.createMalfunctioningProduct -); - -// Get malfunctioning product by ID -router.get( - "/:id", - authenticate, - MalfunctioningProductController.getMalfunctioningProduct -); - -// Update malfunctioning product -router.put( - "/:id", - authenticate, - validateUpdateMalfunctioningProduct, - MalfunctioningProductController.updateMalfunctioningProduct -); - -// Delete malfunctioning product -router.delete( - "/:id", - authenticate, - MalfunctioningProductController.deleteMalfunctioningProduct -); - -// Get all malfunctioning products (with pagination and search) -router.get( - "/", - authenticate, - MalfunctioningProductController.getAllMalfunctioningProducts -); - -// Get count of malfunctioning products by status -router.get( - "/count/:status", - authenticate, - MalfunctioningProductController.getMalfunctioningProductCountByStatus -); - -module.exports = router; diff --git a/backend/routes/sub-routes/supplierRoutes.js b/backend/routes/sub-routes/supplierRoutes.js deleted file mode 100644 index b0fd6295..00000000 --- a/backend/routes/sub-routes/supplierRoutes.js +++ /dev/null @@ -1,50 +0,0 @@ -const express = require("express"); -const router = express.Router(); -const supplierController = require("../controllers/supplierController"); -const productController = require("../controllers/productController"); -const supplierSearchController = require("../controllers/supplierSearchController"); -const supplierFilterController = require("../controllers/supplierFilterController"); -const validateSupplierData = require("../middlewares/validationMiddleware"); -const isAdmin = require("../middlewares/authMiddleware"); - -// Routes for suppliers -router.post( - "/api/suppliers", - isAdmin, - validateSupplierData, - supplierController.createSupplier -); // Admin only -router.get("/api/suppliers", supplierController.getAllSuppliers); -router.get("/api/suppliers/:id", supplierController.getSupplierById); -router.put( - "/api/suppliers/:id", - isAdmin, - validateSupplierData, - supplierController.updateSupplier -); // Admin only -router.delete("/api/suppliers/:id", isAdmin, supplierController.deleteSupplier); // Admin only - -// Routes for managing products supplied by a supplier -router.post( - "/api/suppliers/:id/products", - isAdmin, - productController.addProductToSupplier -); // Admin only -router.delete( - "/api/suppliers/:id/products", - isAdmin, - productController.removeProductFromSupplier -); // Admin only -router.get( - "/api/suppliers/:id/products", - productController.getProductsSupplied -); - -// Routes for searching and filtering suppliers -router.get("/api/suppliers/search", supplierSearchController.searchSuppliers); -router.get( - "/api/suppliers/status/:status", - supplierFilterController.getSuppliersByStatus -); - -module.exports = router; diff --git a/backend/routes/sub-routes/ticketRoutes.js b/backend/routes/sub-routes/ticketRoutes.js deleted file mode 100644 index b9a244aa..00000000 --- a/backend/routes/sub-routes/ticketRoutes.js +++ /dev/null @@ -1,54 +0,0 @@ -const express = require("express"); -const router = express.Router(); -const { - createTicket, - getTicketDetails, - getUserTickets, - getAssignedTickets, - updateTicketStatus, - assignTicket, - closeTicket, - deleteTicket, - getAllTickets, - updateTicketPriority, - getTicketsByStatus, - getTicketsByPriority, -} = require("../../controllers/shop/sub-controllers/ticketController"); - -// Route to create a new ticket -router.post("/tickets", createTicket); - -// Route to get ticket details by ticketId -router.get("/tickets/:ticketId", getTicketDetails); - -// Route to get all tickets for a user -router.get("/user/:userId/tickets", getUserTickets); - -// Route to get all tickets assigned to an agent -router.get("/agent/:agentId/tickets", getAssignedTickets); - -// Route to update ticket status (open, in-progress, resolved, closed) -router.put("/tickets/:ticketId/status", updateTicketStatus); - -// Route to assign a ticket to a support agent -router.put("/tickets/:ticketId/assign", assignTicket); - -// Route to close a ticket -router.put("/tickets/:ticketId/close", closeTicket); - -// Route to delete a ticket -router.delete("/tickets/:ticketId", deleteTicket); - -// Route to get all tickets (Admin only) -router.get("/tickets", getAllTickets); - -// Route to update ticket priority (low, medium, high) -router.put("/tickets/:ticketId/priority", updateTicketPriority); - -// Route to get tickets by status (open, in-progress, resolved, closed) -router.get("/tickets/status/:status", getTicketsByStatus); - -// Route to get tickets by priority (low, medium, high) -router.get("/tickets/priority/:priority", getTicketsByPriority); - -module.exports = router; diff --git a/backend/services/sub-service/couponValidator.js b/backend/services/sub-service/couponValidator.js deleted file mode 100644 index 0ff1e6a0..00000000 --- a/backend/services/sub-service/couponValidator.js +++ /dev/null @@ -1,23 +0,0 @@ -const validateCoupon = async (coupon, orderAmount) => { - const currentDate = new Date(); - - // Check if coupon is expired - if (currentDate < coupon.startDate || currentDate > coupon.endDate) { - return false; - } - - // Check if minimum order amount is met - if (orderAmount < coupon.minOrderAmount) { - return false; - } - - // Check if coupon usage limit has been exceeded - if (coupon.usageCount >= coupon.usageLimit) { - return false; - } - - return true; - }; - - module.exports = { validateCoupon }; - \ No newline at end of file diff --git a/backend/services/sub-service/giftCardUtils.js b/backend/services/sub-service/giftCardUtils.js deleted file mode 100644 index 3e79cbc2..00000000 --- a/backend/services/sub-service/giftCardUtils.js +++ /dev/null @@ -1,54 +0,0 @@ -// Check if a gift card has expired based on its expiry date -exports.isExpired = (expiryDate) => { - const currentDate = new Date(); - return new Date(expiryDate) < currentDate; -}; - -// Format a gift card's value into a currency string (e.g., $100.00) -exports.formatGiftCardValue = (value) => { - return `$${value.toFixed(2)}`; -}; - -// Validate if the gift card value is positive -exports.isValidGiftCardValue = (value) => { - return value > 0; -}; - -// Helper function to generate a random expiration date (within 1 year) -exports.generateRandomExpiryDate = () => { - const currentDate = new Date(); - const randomMonths = Math.floor(Math.random() * 12) + 1; // Expiry in 1 to 12 months - currentDate.setMonth(currentDate.getMonth() + randomMonths); - return currentDate; -}; - -// Helper function to validate card number format (GC-XXXXXXX) -exports.isValidCardNumber = (cardNumber) => { - const regex = /^GC-[A-Z0-9]{9}$/; - return regex.test(cardNumber); -}; - -// Generate a random status for the card (active, redeemed, expired) -exports.generateRandomStatus = () => { - const statuses = ["active", "redeemed", "expired"]; - return statuses[Math.floor(Math.random() * statuses.length)]; -}; - -// Helper function to generate random user ID (for user association) -exports.generateUserId = () => { - return `USR-${Math.random().toString(36).substr(2, 7).toUpperCase()}`; -}; - -// Check if the gift card can be redeemed (it must be active and not expired) -exports.canRedeem = (giftCard) => { - if (giftCard.status !== "active") { - return false; - } - - return !this.isExpired(giftCard.expiryDate); -}; - -// Utility to get the current date in ISO string format -exports.getCurrentDate = () => { - return new Date().toISOString(); -}; diff --git a/backend/services/sub-service/hashPassword.js b/backend/services/sub-service/hashPassword.js deleted file mode 100644 index 0c0a30a2..00000000 --- a/backend/services/sub-service/hashPassword.js +++ /dev/null @@ -1,9 +0,0 @@ - -const bcrypt = require('bcrypt'); - -const hashPassword = async (password) => { - const salt = await bcrypt.genSalt(10); - return bcrypt.hash(password, salt); -}; - -module.exports = { hashPassword }; diff --git a/backend/services/sub-service/logger.js b/backend/services/sub-service/logger.js deleted file mode 100644 index 12b5d108..00000000 --- a/backend/services/sub-service/logger.js +++ /dev/null @@ -1,10 +0,0 @@ - - -exports.logInfo = (message) => { - console.log(`[INFO] ${message}`); - }; - - exports.logError = (message, error) => { - console.error(`[ERROR] ${message}`, error); - }; - \ No newline at end of file diff --git a/backend/services/sub-service/referralFunc.js b/backend/services/sub-service/referralFunc.js deleted file mode 100644 index d66f1d5c..00000000 --- a/backend/services/sub-service/referralFunc.js +++ /dev/null @@ -1,136 +0,0 @@ -const crypto = require("crypto"); - -// Generate a unique referral code with a specified length -function generateReferralCode(length = 8) { - return crypto - .randomBytes(length) - .toString("hex") - .slice(0, length) - .toUpperCase(); -} - -// Check if the referral code format is valid (alphanumeric and of correct length) -function isReferralCodeValid(code, length = 8) { - const regex = new RegExp(`^[A-Z0-9]{${length}}$`); - return regex.test(code); -} - -// Calculate the expiration date of a referral, adding days from the creation date -function calculateExpiryDate(days = 30) { - const expiryDate = new Date(); - expiryDate.setDate(expiryDate.getDate() + days); - return expiryDate; -} - -// Format date to a readable string format -function formatDate(date) { - return `${date.getFullYear()}-${(date.getMonth() + 1) - .toString() - .padStart(2, "0")}-${date.getDate().toString().padStart(2, "0")}`; -} - -// Utility to log referral creation or status changes -function logReferralAction(referralCode, action, referrerId, refereeId = null) { - console.log(`[${new Date().toISOString()}] Referral Action: ${action}`); - console.log(`Referral Code: ${referralCode}`); - console.log(`Referrer ID: ${referrerId}`); - if (refereeId) console.log(`Referee ID: ${refereeId}`); - console.log("------------------------------"); -} - -// Utility function to check if a referral is expired -function isReferralExpired(referral) { - const currentDate = new Date(); - return currentDate > referral.expiryDate; -} - -// Send notification email to the referrer -async function sendReferralNotificationEmail(email, message) { - try { - // Here, you'd use a real email service like SendGrid, Mailgun, etc. - console.log(`Sending email to ${email} with message: ${message}`); - // Example: await emailService.send({ to: email, subject: 'Referral Update', text: message }); - return true; - } catch (error) { - console.error("Failed to send email:", error); - return false; - } -} - -// Validate referrer and referee IDs -function validateUserIds(referrerId, refereeId) { - if (!referrerId || !refereeId) { - throw new Error("Both referrer and referee IDs must be provided"); - } - if (referrerId === refereeId) { - throw new Error("Referrer and referee cannot be the same person"); - } -} - -// Helper to calculate loyalty points based on a referral action -function calculateLoyaltyPoints(actionType) { - switch (actionType) { - case "purchase": - return 10; - case "referral": - return 20; - case "review": - return 5; - default: - return 0; - } -} - -// Fetch paginated results from a referral list (for admin or reporting) -function getPaginatedResults(referralList, page, limit) { - const startIndex = (page - 1) * limit; - const endIndex = page * limit; - return referralList.slice(startIndex, endIndex); -} - -// Generate a secure hash for sensitive referral data -function hashReferralData(data) { - return crypto.createHash("sha256").update(data).digest("hex"); -} - -// Utility function to update referral status -function updateReferralStatus(referral, status) { - if (!["pending", "completed", "expired", "cancelled"].includes(status)) { - throw new Error("Invalid status value"); - } - referral.status = status; -} - -// Utility function to validate status input -function isValidStatus(status) { - return ["pending", "completed", "expired", "cancelled"].includes(status); -} - -// Utility to handle common referral errors -function handleReferralError(error) { - if (error.message.includes("duplicate")) { - return { message: "Duplicate referral code", status: 400 }; - } else if (error.message.includes("expired")) { - return { message: "Referral code has expired", status: 400 }; - } else { - return { message: "An unexpected error occurred", status: 500 }; - } -} - -// Export all utility functions -module.exports = { - generateReferralCode, - isReferralCodeValid, - calculateExpiryDate, - formatDate, - logReferralAction, - isReferralExpired, - sendReferralNotificationEmail, - validateUserIds, - calculateLoyaltyPoints, - getPaginatedResults, - hashReferralData, - updateReferralStatus, - isValidStatus, - handleReferralError, -}; diff --git a/backend/services/sub-service/referralUtils.js b/backend/services/sub-service/referralUtils.js deleted file mode 100644 index 6f9f37f9..00000000 --- a/backend/services/sub-service/referralUtils.js +++ /dev/null @@ -1,8 +0,0 @@ - -exports.generateUniqueCode = () => { - return Math.random().toString(36).substring(2, 10).toUpperCase(); -}; - -exports.validateReferralCodeFormat = (code) => { - return /^[A-Z0-9]{8}$/.test(code); -}; diff --git a/frontend/src/AgroShopAI/components/Pages/Admin-Dashboard.jsx b/frontend/src/AgroShopAI/components/Pages/Admin-Dashboard.jsx deleted file mode 100644 index b61a8644..00000000 --- a/frontend/src/AgroShopAI/components/Pages/Admin-Dashboard.jsx +++ /dev/null @@ -1,33 +0,0 @@ -import { Sidebar } from "./components/Sidebar"; -import { Header } from "./components/Header"; -import { GrievanceList } from "./components/GrievanceList"; -import { DashboardStats } from "./components/DashboardStats"; -import { useState } from "react"; -import StatisticComponent from "./components/StatisticComponent"; -import ReturnPanel from "./components/ReturnPage"; -import AdminProductManagement from "./ProductManagement"; -import ProfileEdit from "./components/ProfileManage"; -export default function AdminDashboard() { - const [activeView, setActiveView] = useState("dashboard"); // Track active view - - // Function to handle view change from Sidebar - const handleViewChange = (view) => { - setActiveView(view); - }; - - return ( -
Manage your agricultural products efficiently
-- - | -handleSort('sku')}>SKU | -handleSort('name')}>Product Name | -handleSort('stock')}>Stock | -handleSort('category')}>Category | -handleSort('seller')}>Seller | -handleSort('location')}>Location | -Actions | -
---|---|---|---|---|---|---|---|
- { - if (selectedItems.includes(item.id)) { - setSelectedItems(selectedItems.filter(id => id !== item.id)) - } else { - setSelectedItems([...selectedItems, item.id]) - } - }} - /> - | -{item.sku} | -{item.name} | -{item.stock} | -{item.category} | -{item.seller} | -{item.location} | -- - - | -
Are you sure you want to delete this item?
-Select a CSV file to upload new inventory items.
- -- Access your agriculture e-commerce dashboard -
-Select a ticket to view details
; - - return ( -User:
-{selectedTicket.user}
-Status:
-- {selectedTicket.status} -
-Priority:
-{selectedTicket.priority}
-Agent:
-{selectedTicket.agent}
-Created:
-{selectedTicket.createdAt}
-Description:
-{selectedTicket.description}
-{subtitle}
- )} -Not a loyalty member?
-Sign up now to access exclusive bundles and additional discounts!
-Original Price: ${calculateTotalPrice(bundle.products).toFixed(2)}
-Bundle Price: ${calculateDiscountedPrice(bundle.products, bundle.discount).toFixed(2)}
-- You Save: $ - {( - calculateTotalPrice(bundle.products) - - calculateDiscountedPrice(bundle.products, bundle.discount) - ).toFixed(2)}{' '} - ({(bundle.discount * 100).toFixed(0)}% off) -
-Original Price: ${calculateTotalPrice(bundle.products).toFixed(2)}
-Bundle Price: ${calculateDiscountedPrice(bundle).toFixed(2)}
-- You Save: $ - {( - calculateTotalPrice(bundle.products) - - calculateDiscountedPrice(bundle) - ).toFixed(2)}{" "} - ({(bundle.discount * 100).toFixed(0)}% off) -
- -${bundle.price.toFixed(2)}
- -Ticket Submitted Successfully!
-Your ticket ID is: {newTicketId}
- -Are you sure you want to delete this item?
-- Discover inspiring stories of farmers who have embraced sustainable - practices and innovative technologies to transform their - agricultural journey. -
-{product.price}
- -Perfect for any gardening enthusiast in your life!
- - Get a Gift Card - -Use code: SPRING20 at checkout
-${product.price.toFixed(2)}
- -{faq.answer}
-Inspire with knowledge and tips
-For examining plants up close
-Organize and preserve seeds
-Plan and track garden progress
-Get the latest deals and gardening tips delivered to your inbox!
- -"{testimonial.text}"
-Posted on: {notice.date}
-{notice.content}
- {isAdmin && ( -{product.price}
- -Date
-{order.date}
-Total Amount
-${order.totalAmount.toFixed(2)}
-Status
-- {order.paymentStatus} -
-{order.shippingDetails.address}
-- {order.shippingDetails.city}, {order.shippingDetails.postalCode} -
-- Order ID - | -- Date - | -- Total Amount - | -- Payment Status - | -- Actions - | -
---|---|---|---|---|
- {order.id} - | -- {order.date} - | -- ${order.totalAmount.toFixed(2)} - | -- - {order.paymentStatus} - - | -- - | -
- Showing{" "} - - {(currentPage - 1) * ordersPerPage + 1} - {" "} - to{" "} - - {Math.min(currentPage * ordersPerPage, dummyOrders.length)} - {" "} - of {dummyOrders.length}{" "} - results -
-${product.price.toFixed(2)} - Stock: {product.stockQuantity}
-Product Management Dashboard
-Manage your products efficiently with AgroShop's powerful admin tools.
-{story.location}
-- {story.cropType} | {story.technology} -
-{story.summary}
- -{story.fullStory}
- -- Manage tickets efficiently and provide exceptional service. -
-
- ID: {selectedTicket.id}
-
- Subject: {selectedTicket.subject}
-
- Status: {selectedTicket.status}
-
- Priority: {selectedTicket.priority}
-
- Description: {selectedTicket.description}
-
- Created At: {selectedTicket.createdAt}
-
- Agent: {selectedTicket.agent}
-
- ID - | -- Subject - | -- Status - | -- Priority - | -- Agent - | -- Created At - | -
---|---|---|---|---|---|
- {ticket.id} - | -- {ticket.subject} - | -- {ticket.status} - | -- {ticket.priority} - | -- {ticket.agent} - | -- {ticket.createdAt} - | -
- We're here to help you. Submit your tickets and get fast support! -
-- - | -handleSort('sku')}>SKU | -handleSort('name')}>Product Name | -handleSort('stock')}>Stock | -handleSort('category')}>Category | -handleSort('seller')}>Seller | -handleSort('location')}>Location | -Actions | -
---|---|---|---|---|---|---|---|
- { - if (selectedItems.includes(item.id)) { - setSelectedItems(selectedItems.filter(id => id !== item.id)); - } else { - setSelectedItems([...selectedItems, item.id]); - } - }} - /> - | -{item.sku} | -{item.name} | -{item.stock} | -{item.category} | -{item.seller} | -{item.location} | -- - - | -
{sellerData.about}
- -No active sessions.
- ) : ( -{dummyData.clicks}
-{dummyData.signUps}
-{dummyData.conversions}
-${dummyData.commissions.toFixed(2)}
-- Partner with us to grow together in sustainable agriculture -
-Earn commissions, access exclusive materials, and help promote sustainable farming practices!
-- Become a partner with AgroShop and earn commissions by promoting our high-quality agricultural products. - Our program offers competitive rates and simple tools to help you maximize your earnings while supporting - sustainable agriculture. -
-- Have questions? Contact us for more information - about how the AgroShop Affiliate Program can work for you. -
-- Access a range of professional marketing tools designed to help you promote AgroShop and increase your earnings. - Use these assets to engage your audience and drive conversions. -
-Choose from a variety of banners tailored to promote AgroShop products effectively.
- - -Use your unique referral link below to start earning commissions:
-Ready-to-post content for Facebook, Instagram, and Twitter.
- -Engage your subscribers with pre-written, customizable email templates.
- -Need custom materials? Contact our support team for assistance.
-- By joining the AgroShop Affiliate Program, you agree to the following terms and conditions: -
-- For any questions, please contact our affiliate support team. -
-Sales trend is {analysis.salesTrend}.
-User registration trend is {analysis.userRegistrationTrend}.
-Top selling product: {analysis.topProduct}
-- Discover the latest and most popular agricultural innovations! Stay - ahead with new technologies. -
- - {/* Call to Action */} -Code | -Type | -Value | -Start Date | -End Date | -Status | -Usage Limit | -Actions | -
---|---|---|---|---|---|---|---|
{coupon.code} | -{coupon.type} | -{coupon.value} | -{coupon.startDate} | -{coupon.endDate} | -{coupon.status} | -{coupon.usageLimit} | -- - - | -
50% accuracy
-Increased by 15%
-95% satisfaction
-Are you sure you want to delete the coupon "{coupon.code}"?
-- Hurry up! Amazing deals await! -
-ID | -Issue | -Date | -Status | -Action | -Delete | -
---|---|---|---|---|---|
{grievance.id} | -{grievance.issue} | -- {grievance.date.toLocaleDateString()} - | -- - | -- - | -- - | -
{message}
-{sellerData.policies[policy]}
- -{product.brand}
-{product.description}
-${product.price.toFixed(2)}
-Are you sure you want to submit the product with the following details?
-- You are about to buy: {product.name} for $ - {product.discountedPrice.toFixed(2)} -
- -{item.name}
-- Returned on: {item.returnDate} -
-Condition: {item.condition}
-Comment: {item.comment}
-{product.model}
-No products returned yet.
- ) : ( -Model: {item.model}
-- Returned on: {item.returnDate} -
-Condition: {item.condition}
-- Comments: {item.comment || "No comments provided"} -
-{request.user.email} | {request.user.phone}
-Order ID: {request.orderId}
-Product: {request.product.name}
-Quantity: {request.product.quantity}
-Price: ${request.product.price.toFixed(2)}
-Reason: {request.reason}
-Submission Date: {request.submissionDate}
-{comment}
- ))} -Model: {product.model}
-Start: {product.startDate}
-End: {product.endDate}
-Welcome, {sellerInfo.name}!
-Store Name: {sellerInfo.storeName}
-Email: {sellerInfo.email}
-Join Date: {sellerInfo.joinDate}
-Seller ID: {sellerInfo.sellerId}
-Location: {sellerInfo.location}
-Phone: {sellerInfo.phone}
-Return Policy: {sellerInfo.returnPolicy}
-Shipping Policy: {sellerInfo.shippingPolicy}
-Payment Methods: {sellerInfo.paymentMethods.join(', ')}
-Price: ₹{product.price}
-Category: {product.category}
-Description: {product.description}
-Stock: {product.stock}
-{value}
-- Discover inspiring stories of farmers who have embraced sustainable practices and innovative technologies to transform their agricultural journey. -
-{story.location}
-{story.cropType} | {story.technology}
-{story.summary}
- -{selectedStory.fullStory}
- -- ${product.price.toFixed(2)} -
- - {/* Add to Cart Button */} - -- By submitting a review, you agree to our{" "} - - Terms and Conditions - - . -
-- Your review may take a few minutes to appear on the page after - submission. -
-{comment}
- Reviewed on {new Date(createdAt).toLocaleDateString()} -Loading reviews...
- ) : ( -