diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/controllers/Controller.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/controllers/Controller.cpp index b0a1c25..77d5a21 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/controllers/Controller.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/controllers/Controller.cpp @@ -10,6 +10,8 @@ Date:19-May-2026 #include "Controller.h" #include "Enums.h" #include "User.h" +#include "ComboPackage.h" +#include "User.h" /* Function: login @@ -72,8 +74,19 @@ const User* Controller::getAuthenticatedUser() return m_authenticationManagementService.getAuthenticatedUser(); } -void Controller::createTechnician(const std::string& username, const std::string& name, const std::string& password, const std::string& email, const std::string& phone) +/* +Function: createTechnician +Description: Creates a new technician account with provided details by + delegating to the user management service. +Parameter: const std::string& username - technician's username + const std::string& password - technician's password + const std::string& email - technician's email address + const std::string& phoneNumber - technician's phone number +Return type: void +*/ +void Controller::createTechnician(const std::string& username, const std::string& name, const std::string& password, const std::string& email, const std::string& phoneNumber) { + m_userManagementService.createUser(username, name, password, email, phoneNumber, util::UserType::TECHNICIAN); } /* @@ -98,9 +111,26 @@ util::Map Controller::getServices() return util::Map(); } +/* +Function: getComboPackages +Description: Retrieves all available combo packages from the service + management service and constructs a read-only map. +Parameter: None +Return type: util::Map +*/ util::Map Controller::getComboPackages() { - return util::Map(); + util::Map currentAvailableComboPackages = m_serviceManagementService.getComboPackages(); + util::Map readOnlyComboPackages; + for (int iterator = 0; iterator < currentAvailableComboPackages.getSize(); iterator++) + { + ComboPackage* currentComboPackage = currentAvailableComboPackages.getValueAt(iterator); + if (currentComboPackage) + { + readOnlyComboPackages.insert(currentComboPackage->getId(), currentComboPackage); + } + } + return readOnlyComboPackages; } /* @@ -131,22 +161,70 @@ void Controller::purchaseComboPackage(const std::string& comboPackageID, const s m_serviceManagementService.purchaseComboPackage(comboPackageID, vehicleNumber, vehicleBrand, vehicleModel); } +/* +Function: getInventoryItems +Description: Retrieves all inventory items from the inventory management service + and constructs a read-only map for external use. +Parameter: None +Return type: util::Map +*/ util::Map Controller::getInventoryItems() { - return util::Map(); + auto inventoryItems = m_inventoryManagementService.getInventoryItems(); + util::Map readOnlyInventoryItems; + int inventoryItemsMapSize = inventoryItems.getSize(); + for (int index = 0; index < inventoryItemsMapSize; index++) + { + readOnlyInventoryItems.insert(inventoryItems.getKeyAt(index), inventoryItems.getValueAt(index)); + } + return readOnlyInventoryItems; } +/* +Function: getInventoryItem +Description: Retrieves a specific inventory item by its ID from the inventory management service. +Parameter: const std::string& inventoryItemID - ID of the inventory item +Return type: const InventoryItem* +*/ const InventoryItem* Controller::getInventoryItem(const std::string& inventoryItemID) { - return nullptr; + return m_inventoryManagementService.getInventoryItem(inventoryItemID); } +/* +Function: addInventoryItem +Description: Adds a new inventory item with specified details to the inventory management service. +Parameter: const std::string& partName - name of the part + int quantity - quantity of the part + double price - price of the part +Return type: void +*/ void Controller::addInventoryItem(const std::string& partName, int quantity, double price) { + m_inventoryManagementService.addInventoryItem(partName, quantity, price); } +/* +Function: removeInventoryItem +Description: Removes an inventory item from the inventory management service by its ID. +Parameter: const std::string& inventoryItemID - ID of the inventory item +Return type: void +*/ void Controller::removeInventoryItem(const std::string& inventoryItemID) { + m_inventoryManagementService.removeInventoryItem(inventoryItemID); +} + +/* +Function: addInventoryItemStock +Description: Adds stock to an existing inventory item in the inventory management service. +Parameter: const std::string& selectedItemId - ID of the inventory item + int quantity - quantity to add +Return type: void +*/ +void Controller::addInventoryItemStock(const std::string& selectedItemId, int quantity) +{ + m_inventoryManagementService.addInventoryItemStock(selectedItemId, quantity); } util::Map Controller::getServiceBookings() @@ -159,9 +237,22 @@ util::Map Controller::getServiceBookingsByUs return util::Map(); } +/* +Function: getUsers +Description: Retrieves all users from the user management service and + constructs a read-only map. +Parameter: None +Return type: util::Map +*/ util::Map Controller::getUsers() { - return util::Map(); + auto listOfUsers = m_userManagementService.getUsers(); + util::Map readOnlyUserList; + for (int iterator = 0; iterator < listOfUsers.getSize(); iterator++) + { + readOnlyUserList.insert(listOfUsers.getKeyAt(iterator), listOfUsers.getValueAt(iterator)); + } + return readOnlyUserList; } util::Map Controller::getUsers(util::UserType userType) @@ -190,16 +281,49 @@ void Controller::completeJob(const std::string& jobID) { } +/* +Function: removeUser +Description: Removes a user by ID. Cancels associated service bookings + and technician jobs before removing the user from the system. +Parameter: const std::string& userID - ID of the user to remove +Return type: void +*/ void Controller::removeUser(const std::string& userID) { + User* user = m_userManagementService.getUser(userID); + if (!user) + { + throw std::runtime_error("Error User not Found.\n"); + } + m_serviceManagementService.cancelCustomerServiceBookings(userID); + m_serviceManagementService.cancelTechnicianJobs(userID); + m_userManagementService.removeUser(userID); } +/* +Function: createComboPackage +Description: Creates a new combo package with specified services and discount + percentage by delegating to the service management service. +Parameter: const std::string& name - name of the combo package + const util::Vector& serviceIDs - list of service IDs + double discountPercentage - discount percentage for the package +Return type: void +*/ void Controller::createComboPackage(const std::string& name, const util::Vector& serviceIDs, double discountPercentage) { + m_serviceManagementService.createComboPackage(name, serviceIDs, discountPercentage); } +/* +Function: removeComboPackage +Description: Removes a combo package by ID by delegating to the service + management service. +Parameter: const std::string& comboPackageID - ID of the combo package +Return type: void +*/ void Controller::removeComboPackage(const std::string& comboPackageID) { + m_serviceManagementService.removeComboPackage(comboPackageID); } util::Map Controller::getInvoicesByUser() diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/controllers/Controller.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/controllers/Controller.h index 1cb9603..9f17d20 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/controllers/Controller.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/controllers/Controller.h @@ -1,24 +1,26 @@ /* File: Controller.h -Description: Header file declaring the Controller class, which coordinates - authentication, user management, service management, inventory, - and notifications across the Vehicle Service System. +Description: Header file declaring the Controller class, which manages + user authentication, inventory, services, bookings, job cards, + invoices, and notifications in the system. Author: Trenser Date:19-May-2026 */ + #pragma once -#include #include "AuthenticationManagementService.h" #include "Enums.h" #include "InventoryManagementService.h" #include "Map.h" #include "PaymentManagementService.h" -#include "ServiceManagementService.h" -#include "UserManagementService.h" -#include "InventoryManagementService.h" -#include "UserManagementService.h" -#include "ServiceManagementService.h" #include "PaymentManagementService.h" +#include "ServiceManagementService.h" +#include "ServiceManagementService.h" +#include "ServiceManagementService.h" +#include "UserManagementService.h" +#include "UserManagementService.h" +#include "UserManagementService.h" +#include class Service; class ComboPackage; @@ -32,9 +34,9 @@ class Notification; class Controller { private: - AuthenticationManagementService m_authenticationManagementService; + AuthenticationManagementService m_authenticationManagementService; UserManagementService m_userManagementService; - ServiceManagementService m_serviceManagementService; + ServiceManagementService m_serviceManagementService; InventoryManagementService m_inventoryManagementService; PaymentManagementService m_paymentManagementService; public: @@ -52,6 +54,7 @@ public: util::Map getInventoryItems(); const InventoryItem* getInventoryItem(const std::string& inventoryItemID); void addInventoryItem(const std::string& partName, int quantity, double price); + void addInventoryItemStock(const std::string& selectedItemId, int quantity); void removeInventoryItem(const std::string& inventoryItemID); util::Map getServiceBookings(); util::Map getServiceBookingsByUser(const std::string userID); diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/JobCard.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/JobCard.cpp index 132e82c..214a8e0 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/JobCard.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/JobCard.cpp @@ -1,10 +1,10 @@ /* File: JobCard.cpp -Description: Implements the JobCard class which represents a technician’s job assignment in the Vehicle Service Management System. - Provides constructors, accessors, and mutators for job details such as ID, booking, service, technician, - assigned date, completion date, and job status. +Description: Implementation file containing the method definitions of the + JobCard class, including constructors, getters, and setters + for job card attributes. Author: Trenser -Date: 19-May-2026 +Date:19-May-2026 */ #include @@ -18,12 +18,10 @@ int JobCard::m_uid = 0; /* Function: JobCard -Description: Default constructor that initializes a new job card with a unique ID, - null booking, null service, null technician, and default job status. -Parameters: - - None -Returns: - - A new JobCard object. +Description: Default constructor that initializes a new job card with + a unique ID and default values. +Parameter: None +Return type: Constructor */ JobCard::JobCard() : m_id("JC" + std::to_string(++m_uid)), diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/JobCard.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/JobCard.h index b8a1cdd..da15959 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/JobCard.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/JobCard.h @@ -1,9 +1,10 @@ /* File: JobCard.h -Description: Declares the JobCard class which represents a technician’s job assignment in the Vehicle Service Management System. - Each job card includes booking details, associated service, technician information, assigned and completion dates, and job status. +Description: Header file declaring the JobCard class, which represents + a service job card containing booking, service, technician, + and status details. Author: Trenser -Date: 19-May-2026 +Date:19-May-2026 */ #pragma once @@ -29,7 +30,6 @@ private: util::Timestamp m_assignedDate; util::ServiceJobStatus m_status; util::Timestamp m_completionDate; - public: JobCard(); JobCard(const std::string& bookingId, diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/ServiceBooking.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/ServiceBooking.cpp index a049a86..8e8b8d7 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/ServiceBooking.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/models/ServiceBooking.cpp @@ -41,8 +41,6 @@ Parameters: - vehicleNumber: Vehicle registration number. - vehicleBrand: Brand of the vehicle. - vehicleModel: Model of the vehicle. - - assignedTechnicianId: ID of the assigned technician. - - assignedTechnician: Name of the assigned technician. - discountPercentage: Discount applied to the booking. Returns: - A new ServiceBooking object. @@ -161,6 +159,12 @@ const util::Vector& ServiceBooking::getServiceIDs() const return m_serviceIDs; } +/* +Function: getServices +Description: Retrieves the services associated with the booking. +Parameter: None +Return type: const util::Map& +*/ /* Function: getServices Description: Retrieves the services associated with the booking. diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/AuthenticationManagementService.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/AuthenticationManagementService.cpp index d6fd4b6..dc3a94c 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/AuthenticationManagementService.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/AuthenticationManagementService.cpp @@ -1,11 +1,12 @@ /* File: AuthenticationManagementService.cpp Description: Implementation file containing the method definitions of the - AuthenticationManagementService class, including login, logout, - password change, and retrieval of the authenticated user. + AuthenticationManagementService class, including logout and + password change logic. Author: Trenser Date:19-May-2026 */ + #include #include "AuthenticationManagementService.h" #include "User.h" diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/AuthenticationManagementService.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/AuthenticationManagementService.h index e89e0c3..47266a1 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/AuthenticationManagementService.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/AuthenticationManagementService.h @@ -6,6 +6,7 @@ Description: Header file declaring the AuthenticationManagementService class, wh Author: Trenser Date:19-May-2026 */ + #pragma once #include #include "DataStore.h" diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/InventoryManagementService.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/InventoryManagementService.cpp index dd702bc..4331e0f 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/InventoryManagementService.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/InventoryManagementService.cpp @@ -20,86 +20,9 @@ Date: 22-May-2026 #include "Utility.h" #include "Vector.h" + util::Map InventoryManagementService::m_observers{}; -/* -Function: attach -Description: Adds a user to the observer list for receiving inventory notifications. -Parameters: - - user: User*, pointer to the user to be attached as an observer -Returns: - - None -*/ -void InventoryManagementService::attach(User* user) -{ - if (user) - { - const std::string& userID = user->getId(); - if (m_observers.find(userID) == -1) - { - m_observers[userID] = user; - } - } -} - -/* -Function: detach -Description: Removes a user from the observer list so they no longer receive inventory notifications. -Parameters: - - user: User*, pointer to the user to be detached from the observer list -Returns: - - None -*/ -void InventoryManagementService::detach(User* user) -{ - if (user) - { - const std::string& userID = user->getId(); - if (m_observers.find(userID) != -1) - { - m_observers.remove(userID); - } - } -} - -/* -Function: sendNotification -Description: Sends a notification to a user if they are subscribed as an observer. -Parameters: - - user: User*, pointer to the user receiving the notification - - title: std::string, title of the notification - - message: std::string, body/content of the notification -Returns: - - None -Throws: - - std::runtime_error if notification creation fails -*/ -void InventoryManagementService::sendNotification(User* user, const std::string& title, const std::string& message) -{ - if (user) - { - if (m_observers.find(user->getId()) != -1) - { - Notification* notification = - Factory::getObject( - user->getId(), - user, - "InventoryManagementService: " + title, - message, - util::Timestamp() - ); - if (notification) - { - user->addNotification(notification); - } - else - { - throw std::runtime_error("Failed to create notification"); - } - } - } -} - /* Function: sendLowStockAlertsToAdmins (static helper) Description: Sends low stock alert notifications to all admin users for a given inventory item. @@ -250,4 +173,165 @@ Returns: void InventoryManagementService::saveObservers() { util::saveObservers(config::file::INVENTORYMANAGEMENTOBSERVERS, this); -} \ No newline at end of file +} + +/* +Function: addInventoryItem +Description: Creates a new inventory item using the Factory and inserts it + into the DataStore. +Parameter: const std::string& partName - name of the part + int quantity - initial quantity of the part + double price - price of the part +Return type: void +*/ +void InventoryManagementService::addInventoryItem(const std::string& partName, int quantity, double price) +{ + InventoryItem* newItem = Factory::getObject(partName, quantity, price); + m_dataStore.getInventoryItems().insert(newItem->getId(), newItem); +} + +/* +Function: addInventoryItemStock +Description: Increases the stock quantity of an existing inventory item. +Parameter: const std::string& selectedItemId - ID of the inventory item + int quantity - quantity to add +Return type: void +*/ +void InventoryManagementService::addInventoryItemStock(const std::string& selectedItemId, int quantity) +{ + int index = m_dataStore.getInventoryItems().find(selectedItemId); + if (index != -1) + { + InventoryItem* item = m_dataStore.getInventoryItems().getValueAt(index); + if (item != nullptr) + { + int totalQuantity = item->getQuantity() + quantity; + item->setQuantity(totalQuantity); + } + } +} + +/* +Function: getInventoryItems +Description: Retrieves all inventory items stored in the DataStore. +Parameter: None +Return type: util::Map +*/ +util::Map InventoryManagementService::getInventoryItems() +{ + return m_dataStore.getInventoryItems(); +} + +/* +Function: removeInventoryItem +Description: Marks an inventory item as inactive instead of deleting it. +Parameter: const std::string& inventoryItemID - ID of the inventory item +Return type: void +*/ +void InventoryManagementService::removeInventoryItem(const std::string& inventoryItemID) +{ + int index = m_dataStore.getInventoryItems().find(inventoryItemID); + if (index != -1) + { + InventoryItem* item = m_dataStore.getInventoryItems().getValueAt(index); + if (item != nullptr) + { + item->setState(util::State::INACTIVE); + } + } +} + +/* +Function: getInventoryItem +Description: Retrieves a specific inventory item by its ID from the DataStore. +Parameter: const std::string& inventoryItemID - ID of the inventory item +Return type: InventoryItem* +*/ +InventoryItem* InventoryManagementService::getInventoryItem(const std::string& inventoryItemID) +{ + int index = m_dataStore.getInventoryItems().find(inventoryItemID); + if (index != -1) + { + return m_dataStore.getInventoryItems().getValueAt(index); + } + return nullptr; +} + +/* +Function: attach +Description: Adds a user to the observer list for receiving inventory notifications. +Parameters: + - user: User*, pointer to the user to be attached as an observer +Returns: + - None +*/ +void InventoryManagementService::attach(User* user) +{ + if (user) + { + const std::string& userID = user->getId(); + if (m_observers.find(userID) == -1) + { + m_observers[userID] = user; + } + } +} + +/* +Function: detach +Description: Removes a user from the observer list so they no longer receive inventory notifications. +Parameters: + - user: User*, pointer to the user to be detached from the observer list +Returns: + - None +*/ +void InventoryManagementService::detach(User* user) +{ + if (user) + { + const std::string& userID = user->getId(); + if (m_observers.find(userID) != -1) + { + m_observers.remove(userID); + } + } +} + +/* +Function: sendNotification +Description: Sends a notification to a user if they are subscribed as an observer. +Parameters: + - user: User*, pointer to the user receiving the notification + - title: std::string, title of the notification + - message: std::string, body/content of the notification +Returns: + - None +Throws: + - std::runtime_error if notification creation fails +*/ +void InventoryManagementService::sendNotification(User* user, const std::string& title, const std::string& message) +{ + if (user) + { + if (m_observers.find(user->getId()) != -1) + { + Notification* notification = + Factory::getObject( + user->getId(), + user, + "InventoryManagementService: " + title, + message, + util::Timestamp() + ); + if (notification) + { + user->addNotification(notification); + } + else + { + throw std::runtime_error("Failed to create notification"); + } + } + } +} + diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/InventoryManagementService.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/InventoryManagementService.h index a56cd37..f5db383 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/InventoryManagementService.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/InventoryManagementService.h @@ -1,9 +1,10 @@ /* File: InventoryManagementService.h -Description: Declares the InventoryManagementService class which manages inventory operations in the Vehicle Service Management System. - Provides functionality to retrieve, add, and remove inventory items, send low stock alerts, and handle notifications using the Observer pattern. +Description: Header file declaring the InventoryManagementService class, + which manages inventory items, stock updates, and notifications + related to low stock alerts. Inherits from NotificationManagementService. Author: Trenser -Date: 19-May-2026 +Date:19-May-2026 */ #pragma once @@ -27,6 +28,7 @@ public: InventoryItem* getInventoryItem(const std::string& inventoryItemID); void addInventoryItem(const std::string& partName, int quantity, double price); void removeInventoryItem(const std::string& inventoryItemID); + void addInventoryItemStock(const std::string& selectedItemId, int quantity); void sendLowStockAlerts(); void sendNotification(User* user, const std::string& title, const std::string& message) override; void attach(User* user) override; diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/ServiceManagementService.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/ServiceManagementService.cpp index 54210e8..a6b97df 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/ServiceManagementService.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/ServiceManagementService.cpp @@ -11,11 +11,15 @@ Date:19-May-2026 #include "AuthenticationManagementService.h" #include "ComboPackage.h" #include "Config.h" +#include "DataStore.h" #include "Factory.h" #include "FileManager.h" +#include "InventoryItem.h" #include "JobCard.h" #include "Service.h" #include "ServiceBooking.h" +#include "ServiceBooking.h" + #include "ServiceManagementService.h" #include "Timestamp.h" #include "User.h" @@ -499,4 +503,225 @@ Returns: void ServiceManagementService::saveObservers() { util::saveObservers(config::file::SERVICEMANAGEMENTOBSERVERS, this); -} \ No newline at end of file +} + +/* +Function: cancelCustomerServiceBookings +Description: Cancels all service bookings associated with a given customer or technician. + Updates booking status, resets customer/technician assignments, sends notifications, + and restocks inventory items. +Parameter: const std::string& userID - ID of the customer or technician +Return type: void +*/ +void ServiceManagementService::cancelCustomerServiceBookings(const std::string& userID) +{ + const int INCREMENT_VALUE = 1; + auto& users = m_dataStore.getUsers(); + int userIndex = users.find(userID); + if (userIndex == -1) + { + throw std::runtime_error("User not found: " + userID); + } + User* user = users.getValueAt(userIndex); + if (user == nullptr) + { + throw std::runtime_error("User not found: " + userID); + } + util::UserType type = user->getUserType(); + auto& bookings = DataStore::getInstance().getServiceBookings(); + for (int bookingIterator = 0; bookingIterator < bookings.getSize(); bookingIterator++) + { + ServiceBooking* booking = bookings.getValueAt(bookingIterator); + if (booking != nullptr && + (booking->getCustomerId() == userID || booking->getAssignedTechnicianId() == userID)) + { + if (booking->getStatus() == util::ServiceJobStatus::PENDING || + booking->getStatus() == util::ServiceJobStatus::STARTED) + { + if (type == util::UserType::CUSTOMER) + { + booking->setStatus(util::ServiceJobStatus::CANCELLED); + booking->setCustomer(nullptr); + booking->setCustomerId(""); + User* assignedTechnician = booking->getAssignedTechnician(); + std::string title = "Customer Service Cancelled"; + std::string message = "The customer has cancelled their service booking. Your assigned job card has been cancelled and the inventory has been restocked."; + sendNotification(assignedTechnician, title, message); + } + else if (type == util::UserType::TECHNICIAN) + { + booking->setStatus(util::ServiceJobStatus::PENDING); + std::string title = "Technician Unavailable"; + std::string message = "Your assigned technician is no longer available. Your booking has been reset to pending, and we will reassign a new technician shortly."; + sendNotification(booking->getCustomer(), title, message); + } + booking->setAssignedTechnician(nullptr); + booking->setAssignedTechnicianId(""); + const auto& ListOfServices = booking->getServices(); + for (int serviceIterator = 0; serviceIterator < ListOfServices.getSize(); serviceIterator++) + { + Service* service = ListOfServices.getValueAt(serviceIterator); + if (service != nullptr) + { + const auto& items = service->getRequiredInventoryItems(); + for (int itemIterator = 0; itemIterator < items.getSize(); itemIterator++) + { + InventoryItem* item = items.getValueAt(itemIterator); + if (item != nullptr) + { + item->setQuantity(item->getQuantity() + INCREMENT_VALUE); + } + } + } + } + } + } + } +} + +/* +Function: cancelTechnicianJobs +Description: Cancels all jobs assigned to a technician. Updates job status, sends notifications, + and restocks inventory items used in the service. +Parameter: const std::string& technicianID - ID of the technician +Return type: void +*/ +void ServiceManagementService::cancelTechnicianJobs(const std::string& technicianID) +{ + const int INCREMENT_VALUE = 1; + auto& jobs = m_dataStore.getJobCards(); + for (int jobIterator = 0; jobIterator < jobs.getSize(); jobIterator++) + { + JobCard* job = jobs.getValueAt(jobIterator); + if (job != nullptr && job->getTechnicianId() == technicianID) + { + if (job->getStatus() == util::ServiceJobStatus::PENDING || job->getStatus() == util::ServiceJobStatus::STARTED) + { + job->setStatus(util::ServiceJobStatus::CANCELLED); + std::string title = "Job Cancelled"; + std::string message = "The Job has cancelled. Your job card has been cancelled and the inventory has been restocked."; + sendNotification(job->getTechnician(), title, message); + Service* service = job->getService(); + if (service != nullptr) + { + const auto& items = service->getRequiredInventoryItems(); + for (int itemIterator = 0; itemIterator < items.getSize(); itemIterator++) + { + InventoryItem* item = items.getValueAt(itemIterator); + if (item != nullptr) + { + item->setQuantity(item->getQuantity() + INCREMENT_VALUE); + } + } + } + } + } + } +} + +/* +Function: createComboPackage +Description: Creates a new combo package with two services and a discount percentage. + Validates service IDs, ensures uniqueness, and inserts the new package into the DataStore. +Parameter: const std::string& packageName - name of the combo package + const util::Vector& serviceIDsInNewCombo - list of service IDs + double discountPercentage - discount percentage for the package +Return type: void +*/ +void ServiceManagementService::createComboPackage(const std::string& packageName, const util::Vector& serviceIDsInNewCombo, double discountPercentage) +{ + if (packageName.empty()) + { + throw std::invalid_argument("The Combo Package Name cannot be empty.\n"); + } + if (serviceIDsInNewCombo.getSize() < 2 || serviceIDsInNewCombo.getSize() > 2) + { + throw std::invalid_argument("Combo package must contain only two services."); + } + if (discountPercentage < 0.0 || discountPercentage > 100.0) + { + throw std::invalid_argument("Discount percentage must be between 0 and 100."); + } + auto& servicesMap = m_dataStore.getServices(); + for (int index = 0; index < serviceIDsInNewCombo.getSize(); index++) + { + const std::string serviceid = serviceIDsInNewCombo[index]; + if (servicesMap.find(serviceid) == -1) + { + throw std::runtime_error("Service ID not found: " + serviceid); + } + } + auto& comboPackageMap = m_dataStore.getComboPackages(); + for (int iterator = 0; iterator < comboPackageMap.getSize(); iterator++) + { + ComboPackage* existingCombos = comboPackageMap.getValueAt(iterator); + const util::Map& servicesInsideExistingCombos = existingCombos->getServices(); + if (servicesInsideExistingCombos.getSize() == serviceIDsInNewCombo.getSize()) + { + bool isIdentical = true; + for (int serviceIterator = 0; serviceIterator < serviceIDsInNewCombo.getSize(); serviceIterator++) + { + const std::string& id = serviceIDsInNewCombo[serviceIterator]; + if (servicesInsideExistingCombos.find(id) == -1) + { + isIdentical = false; + break; + } + } + if (isIdentical) + { + throw std::runtime_error("A combo package with the same services already exists."); + } + } + } + util::Map selectedServices; + for (int iteratorOne = 0; iteratorOne < serviceIDsInNewCombo.getSize(); iteratorOne++) + { + const std::string& serviceId = serviceIDsInNewCombo[iteratorOne]; + int serviceIndex = servicesMap.find(serviceId); + if (serviceIndex == -1) + { + throw std::runtime_error("Service ID not found: " + serviceId); + } + selectedServices.insert(serviceId, servicesMap.getValueAt(serviceIndex)); + } + ComboPackage* newComboPackage = Factory::getObject(packageName, discountPercentage, selectedServices); + comboPackageMap.insert(newComboPackage->getId(), newComboPackage); +} + +/* +Function: getComboPackages +Description: Retrieves all combo packages stored in the DataStore. +Parameter: None +Return type: util::Map +*/ +util::Map ServiceManagementService::getComboPackages() +{ + return m_dataStore.getComboPackages(); +} + +/* +Function: removeComboPackage +Description: Removes a combo package by marking it inactive. Throws an exception if the package ID is not found. +Parameter: const std::string& comboPackageID - ID of the combo package +Return type: void +*/ +void ServiceManagementService::removeComboPackage(const std::string& comboPackageID) +{ + bool removed = false; + util::Map& currentComboPackages = m_dataStore.getComboPackages(); + for (int iterator = 0; iterator < currentComboPackages.getSize(); iterator++) + { + ComboPackage* currentComboPackage = currentComboPackages.getValueAt(iterator); + if (currentComboPackage && currentComboPackage->getId() == comboPackageID) + { + currentComboPackage->setState(util::State::INACTIVE); + removed = true; + break; + } + } + if (!removed) + { + throw std::runtime_error("Combo package with ID '" + comboPackageID + "' not found."); + } +} diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/ServiceManagementService.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/ServiceManagementService.h index 119af04..bee1dd5 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/ServiceManagementService.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/ServiceManagementService.h @@ -6,6 +6,7 @@ Description: Header file declaring the ServiceManagementService class, which man Author: Trenser Date:19-May-2026 */ + #pragma once #include #include "Map.h" @@ -38,7 +39,7 @@ public: void completeJob(const std::string& jobID); void cancelCustomerServiceBookings(const std::string& customerID); void cancelTechnicianJobs(const std::string& technicianID); - void createComboPackage(const std::string& name, const util::Vector& serviceIDs, double discountPercentage); + void createComboPackage(const std::string& packageName, const util::Vector& serviceIDs, double discountPercentage); void removeComboPackage(const std::string& comboPackageID); void sendNotification(User* user, const std::string& title, const std::string& message) override; void attach(User* user) override; diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/UserManagementService.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/UserManagementService.cpp index 0503019..8267144 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/UserManagementService.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/services/UserManagementService.cpp @@ -6,7 +6,6 @@ Description: Implementation file containing the method definitions of the Author: Trenser Date:19-May-2026 */ -#include #include "Config.h" #include "Enums.h" #include "Factory.h" @@ -18,6 +17,7 @@ Date:19-May-2026 #include "User.h" #include "UserManagementService.h" #include "Vector.h" +#include /* @@ -243,4 +243,50 @@ void UserManagementService::saveUsers() } userFileManager.save(users); notificationFileManager.save(notifications); +} + +/* +Function: getUsers +Description: Retrieves all users stored in the DataStore. +Parameter: None +Return type: util::Map +*/ +util::Map UserManagementService::getUsers() +{ + return m_dataStore.getUsers(); +} + +/* +Function: getUser +Description: Retrieves a specific user by ID from the DataStore. +Parameter: const std::string& userID - ID of the user +Return type: User* +*/ +User* UserManagementService::getUser(const std::string& userID) +{ + int index = m_dataStore.getUsers().find(userID); + if (index != -1) + { + return m_dataStore.getUsers().getValueAt(index); + } + return nullptr; +} + +/* +Function: removeUser +Description: Marks a user as inactive in the DataStore instead of deleting them. +Parameter: const std::string& userID - ID of the user to remove +Return type: void +*/ +void UserManagementService::removeUser(const std::string& userID) +{ + int index = m_dataStore.getUsers().find(userID); + if (index != -1) + { + User* user = m_dataStore.getUsers().getValueAt(index); + if (user != nullptr) + { + user->setState(util::State::INACTIVE); + } + } } \ No newline at end of file diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/utilities/Enums.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/utilities/Enums.h index 9e8b1b9..c738baa 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/utilities/Enums.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/utilities/Enums.h @@ -33,8 +33,10 @@ namespace util enum class ServiceJobStatus { + PENDING, STARTED, - COMPLETED + COMPLETED, + CANCELLED }; enum class State @@ -192,10 +194,14 @@ namespace util { switch (status) { + case ServiceJobStatus::PENDING: + return "PENDING"; case ServiceJobStatus::STARTED: return "STARTED"; case ServiceJobStatus::COMPLETED: return "COMPLETED"; + case ServiceJobStatus::CANCELLED: + return "CANCELLED"; } throw std::invalid_argument("Invalid ServiceJobStatus"); } @@ -220,6 +226,14 @@ namespace util { return ServiceJobStatus::COMPLETED; } + if (value == "PENDING") + { + return ServiceJobStatus::PENDING; + } + if (value == "CANCELLED") + { + return ServiceJobStatus::CANCELLED; + } throw std::invalid_argument("Invalid ServiceJobStatus string"); } diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/utilities/Utility.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/utilities/Utility.h index 396fd4b..6f473fd 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/utilities/Utility.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/utilities/Utility.h @@ -1,18 +1,18 @@ /* File: Utility.h -Description: Header file declaring utility functions used across the system, - including cost calculation for services and combo packages. +Description: Header file declaring utility functions used across the system Author: Trenser Date:19-May-2026 */ #pragma once +#include "ComboPackage.h" #include "DataStore.h" #include "FileHelper.h" #include "InventoryItem.h" +#include "InventoryItem.h" #include "NotificationManagementService.h" #include "Service.h" -#include "ComboPackage.h" namespace util { diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/AdminMenu.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/AdminMenu.cpp index 4e81925..3c21e74 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/AdminMenu.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/AdminMenu.cpp @@ -8,72 +8,286 @@ Author: Trenser Date: 19-May-2026 */ +#include +#include #include "AdminMenu.h" +#include "ComboPackage.h" +#include "Enums.h" #include "InputHelper.h" -#include "OutputHelper.h" +#include "InventoryItem.h" #include "MenuHelper.h" +#include "OutputHelper.h" +#include "Service.h" +#include "User.h" +#include "Utility.h" +#include "Validator.h" /* Function: showMenu -Description: Displays the admin menu in a loop until the user chooses to logout. - Handles exceptions and ensures smooth user interaction. -Parameters: - - None -Returns: - - void +Description: Displays the admin menu and handles user input until logout is selected. +Parameter: None +Return type: void */ void AdminMenu::showMenu() { - bool isMenuActive = true; - while (isMenuActive) + while (true) + { + try + { + int choice; + util::clear(); + std::cout << "Admin Menu" + << "\n1. View Stock Levels" + << "\n2. Add Inventory Item" + << "\n3. Remove Inventory Item" + << "\n4. Check Stock Availability" + << "\n5. Assign Job to Technician" + << "\n6. Add Technician" + << "\n7. Remove Customer/Technician" + << "\n8. Create Service" + << "\n9. Remove Service" + << "\n10. Create Combo Package" + << "\n11. Remove Combo Package" + << "\n12. View Notifications" + << "\n13. Change Password" + << "\n14. Logout" + << "\nEnter a choice: "; + util::read(choice); + if (!handleOperation(choice)) + { + break; + } + } + catch (const std::exception& e) + { + std::cout << "Exception: " << e.what() << std::endl; + util::pressEnter(); + } + } +} + +/* +Function: handleOperation +Description: Executes the corresponding admin operation based on the selected menu choice. +Parameter: int choice - selected menu option +Return type: bool - true if menu continues, false if logout +*/ +bool AdminMenu::handleOperation(int choice) +{ + switch (choice) + { + case 1: + viewStockLevels(); + break; + case 2: + addInventoryItem(); + break; + case 3: + removeInventoryItem(); + break; + case 4: + checkStockAvailability(); + break; + case 5: + assignJob(); + break; + case 6: + addTechnician(); + break; + case 7: + removeUser(); + break; + case 8: + createService(); + break; + case 9: + removeService(); + break; + case 10: + createComboPackages(); + break; + case 11: + removeComboPackage(); + break; + case 12: + viewNotifications(); + break; + case 13: + changePassword(); + break; + case 14: + logout(); + return false; + default: + std::cout << "Enter a valid choice!" << std::endl; + util::pressEnter(); + } + return true; +} + +/* +Function: logout +Description: Logs out the currently authenticated admin user. +Parameter: None +Return type: void +*/ +void AdminMenu::logout() +{ + m_controller.logout(); +} + +/* +Function: changePassword +Description: Allows the admin to change their password after validation. +Parameter: None +Return type: void +*/ +void AdminMenu::changePassword() +{ + changePasswordHelper(m_controller); +} + +/* +Function: viewStockLevels +Description: Displays all active inventory items with their details + including ID, part name, quantity, and price. +Parameter: None +Return type: void +*/ +void AdminMenu::viewStockLevels() +{ + util::clear(); + auto inventoryItems = m_controller.getInventoryItems(); + std::cout << std::left << std::setw(15) << "Item ID" + << std::setw(25) << "Part Name" + << std::setw(10) << "Quantity" + << std::setw(10) << "Price" + << std::endl; + for (int iterator = 0; iterator < inventoryItems.getSize(); ++iterator) { - try + const InventoryItem* item = inventoryItems.getValueAt(iterator); + if (item != nullptr) { - int choice; - util::clear(); - std::cout << "" << std::endl; - util::read(choice); - if (!handleOperation(choice)) + if (item->getState() != util::State::INACTIVE) { - isMenuActive = false; + std::cout << std::left << std::setw(15) << item->getId() + << std::setw(25) << item->getPartName() + << std::setw(10) << item->getQuantity() + << std::setw(10) << item->getPrice() + << std::endl; } } - catch (const std::exception& e) - { - std::cout << "Exception: " << e.what() << std::endl; - util::pressEnter(); - } } } -bool AdminMenu::handleOperation(int choice) -{ - return false; -} - - -void AdminMenu::logout() -{ -} - -void AdminMenu::changePassword() -{ -} - -void AdminMenu::viewStockLevels() -{ -} - +/* +Function: addInventoryItem +Description: Allows the admin to either add a new inventory item + or increase the quantity of an existing item. +Parameter: None +Return type: void +*/ void AdminMenu::addInventoryItem() { + util::clear(); + int choice, quantity; + double price; + std::string partName; + std::cout << "1. Add new item \n2. Add Quantity\nEnter your choice : "; + util::read(choice); + switch (choice) + { + case 1: + { + std::cout << "--------Enter Item Details----------\n"; + std::cout << "Part Name : "; + util::read(partName); + std::cout << "Quantity : "; + util::read(quantity); + std::cout << "Price : "; + util::read(price); + m_controller.addInventoryItem(partName, quantity, price); + std::cout << "New Item " << partName << " added to the Inventory.\n"; + break; + } + case 2: + { + auto inventoryItems = m_controller.getInventoryItems(); + addQuantityToItem(inventoryItems, m_controller); + break; + } + } + util::pressEnter(); } +/* +Function: removeInventoryItem +Description: Removes an active inventory item by marking it inactive + after user selection. +Parameter: None +Return type: void +*/ void AdminMenu::removeInventoryItem() { + util::clear(); + auto inventoryItems = m_controller.getInventoryItems(); + auto activeItems = filterActiveItems(inventoryItems); + int activeItemsSize = activeItems.getSize(); + if (activeItemsSize == 0) + { + std::cout << "No items available in Inventory." << std::endl; + util::pressEnter(); + return; + } + displayInventoryWithItems(activeItems); + int itemIndex; + std::cout << "Enter the index of the item to remove: "; + util::read(itemIndex); + if (itemIndex < 1 || itemIndex > activeItemsSize) + { + std::cout << "Invalid index selected." << std::endl; + util::pressEnter(); + return; + } + const InventoryItem* selectedItem = activeItems.getValueAt(itemIndex - 1); + if (selectedItem != nullptr) + { + if(selectedItem->getState() != util::State::INACTIVE) + { + std::string selectedItemId = selectedItem->getId(); + m_controller.removeInventoryItem(selectedItemId); + std::cout << "Item " << selectedItem->getPartName() << " removed successfully." << std::endl; + } + } + util::pressEnter(); } +/* +Function: checkStockAvailability +Description: Checks if a specific inventory item is available + and displays its details if active. +Parameter: None +Return type: void +*/ void AdminMenu::checkStockAvailability() { + util::clear(); + std::string itemId; + std::cout << "Enter the Item Id : "; + util::read(itemId); + const InventoryItem* selectedItem = m_controller.getInventoryItem(itemId); + if (selectedItem != nullptr) + { + if (selectedItem->getState() != util::State::INACTIVE) + { + std::cout << "Item Details\n"; + std::cout << "---------------------------------------------\n"; + std::cout << "Item ID : " << selectedItem->getId() << "\n"; + std::cout << "Part Name : " << selectedItem->getPartName() << "\n"; + std::cout << "Quantity : " << selectedItem->getQuantity() << "\n"; + } + } + util::pressEnter(); } void AdminMenu::assignJob() @@ -88,20 +302,168 @@ void AdminMenu::removeService() { } +/* +Function: addTechnician +Description: Adds a new technician after validating username, password, email, and phone number. +Parameter: None +Return type: void +*/ void AdminMenu::addTechnician() { + util::clear(); + std::string username, name, password, email, phoneNumber; + std::cout << std::left << std::setw(25) << "Enter Technician Username: "; + util::read(username); + std::cout << std::left << std::setw(25) << "Enter Technician Name: "; + util::read(name); + std::cout << std::setw(25) << "Enter Technician Password: "; + util::read(password); + if(!util::isPasswordValid(password)) + { + std::cout << "Error: Password is invalid!"; + util::pressEnter(); + return; + } + std::cout << std::setw(25) << "Enter Technician Email: "; + util::read(email); + if(!util::isEmailValid(email)) + { + std::cout << "Error: Email is invalid!"; + util::pressEnter(); + return; + } + std::cout << std::setw(25) << "Enter Technician Phone: "; + util::read(phoneNumber); + if(!util::isPhoneNumberValid(phoneNumber)) + { + std::cout << "Error: Phone Number is invalid!"; + util::pressEnter(); + return; + } + m_controller.createTechnician(username, name, password, email, phoneNumber); + std::cout << "\nTechnician Added Successfully.\n"; + util::pressEnter(); } +/* +Function: removeUser +Description: Removes a selected active user (customer or technician) from the system. +Parameter: None +Return type: void +*/ void AdminMenu::removeUser() { + util::clear(); + int indexChoice; + auto listOfUsers = m_controller.getUsers(); + auto listOfActiveUsers = filterActiveUsers(listOfUsers); + int activeUserCount = listOfActiveUsers.getSize(); + if (activeUserCount < 1) + { + std::cout << "No Active users." << std::endl; + util::pressEnter(); + return; + } + displayAllActiveUsers(listOfActiveUsers, activeUserCount); + std::cout << "Enter the index of the user to delete : "; + util::read(indexChoice); + if (indexChoice < 1 || indexChoice > activeUserCount) + { + std::cout << "Error Invaild index.\n" << std::endl; + util::pressEnter(); + return; + } + const User* userToRemove = listOfActiveUsers.getValueAt(indexChoice - 1); + if (userToRemove != nullptr) + { + std::string userIdToRemove = userToRemove->getId(); + m_controller.removeUser(userIdToRemove); + std::cout << userToRemove->getUserName() << " removed Successfully.\n"; + } + util::pressEnter(); } +/* +Function: createComboPackages +Description: Creates a new combo package by selecting two active services and applying a discount. +Parameter: None +Return type: void +*/ void AdminMenu::createComboPackages() { + util::clear(); + auto serviceList = m_controller.getServices(); + const int NUMBER_OF_SERVICE_PER_PACKAGE = 2; + util::Vector selectedServiceID; + for (int iterator = 0; iterator < NUMBER_OF_SERVICE_PER_PACKAGE; iterator++) + { + const Service* chosenService = nullptr; + while (true) + { + chosenService = selectServiceFromServices(serviceList); + if (chosenService == nullptr) + { + std::cout << "Failed to create combo package!"; + util::pressEnter(); + return; + } + bool alreadyChosen = false; + for (int iteratorOne = 0; iteratorOne < selectedServiceID.getSize(); iteratorOne++) + { + if (selectedServiceID[iteratorOne] == chosenService->getId()) + { + alreadyChosen = true; + break; + } + } + if (alreadyChosen) + { + std::cout << "Service already selected. Please choose a different one." << std::endl; + continue; + } + selectedServiceID.push_back(chosenService->getId()); + util::clear(); + break; + } + } + std::string packageName; + double discountPercentage; + std::cout << "Enter combo package name: "; + util::read(packageName); + std::cout << "Enter discount percentage: "; + util::read(discountPercentage); + if (discountPercentage < 0.0 || discountPercentage > 100.0) + { + std::cout << "Error: Discount percentage must be between 0 and 100." << std::endl; + util::pressEnter(); + return; + } + m_controller.createComboPackage(packageName, selectedServiceID, discountPercentage); + std::cout << "Combo package '" << packageName << "' created successfully." << std::endl; + util::pressEnter(); } +/* +Function: removeComboPackage +Description: Removes a selected combo package from the system. +Parameter: None +Return type: void +*/ void AdminMenu::removeComboPackage() { + util::clear(); + util::Map currentComboPackages = m_controller.getComboPackages(); + std::string selectedComboPackageID = selectComboPackage(currentComboPackages); + if (selectedComboPackageID != "") + { + m_controller.removeComboPackage(selectedComboPackageID); + std::cout << "Combo Package removed successfully.\n"; + } + else + { + std::cout << "Combo package removal failed.\n"; + } + util::pressEnter(); } /* diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/AdminMenu.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/AdminMenu.h index cc4ff2f..8b1b31f 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/AdminMenu.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/AdminMenu.h @@ -1,10 +1,10 @@ /* File: AdminMenu.h -Description: Declares the AdminMenu class which provides the administrative console menu in the Vehicle Service Management System. - Supports operations such as inventory management, job assignment, service creation/removal, technician management, - combo package handling, notification viewing, and account management functions like logout and password change. +Description: Header file declaring the AdminMenu class, which provides + administrative operations such as inventory management, + user management, service configuration, and notifications. Author: Trenser -Date: 19-May-2026 +Date:19-May-2026 */ #pragma once diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/MenuHelper.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/MenuHelper.h index 0bb708b..9dfc41d 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/MenuHelper.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/MenuHelper.h @@ -8,8 +8,10 @@ Date: 21-May-2026 */ #pragma once +#include #include #include +#include "Utility.h" #include "Controller.h" #include "InputHelper.h" #include "Map.h" @@ -125,6 +127,7 @@ Return type: void */ inline void changePasswordHelper(Controller& controller) { + util::clear(); std::string newPassword; while (true) { @@ -144,6 +147,61 @@ inline void changePasswordHelper(Controller& controller) } } +/* +Function: filterActiveUsers +Description: Filters out inactive users and returns a map of active users. +Parameter: const util::Map& listOfUsers - all users +Return type: util::Map +*/ +inline util::Map filterActiveUsers(const util::Map& listOfUsers) +{ + util::Map activeUsers; + int inventorySize = listOfUsers.getSize(); + for (int index = 0; index < inventorySize; index++) + { + const User* user = listOfUsers.getValueAt(index); + if (user != nullptr && user->getState() != util::State::INACTIVE) + { + activeUsers.insert(user->getId(), user); + } + } + return activeUsers; +} + +/* +Function: displayAllActiveUsers +Description: Displays all active users in a tabular format with index, ID, username, and type. +Parameter: util::Map& activeUsers - active users list + int activeUserCount - number of active users +Return type: void +*/ +inline void displayAllActiveUsers(util::Map& activeUsers, int activeUserCount) +{ + std::cout << std::left << std::setw(10) << "Index" + << std::setw(15) << "User ID" + << std::setw(25) << "Username" + << std::setw(25) << "User Type" + << std::endl; + for (int iterator = 0; iterator < activeUserCount; iterator++) + { + const User* user = activeUsers.getValueAt(iterator); + if (user != nullptr) + { + std::cout << std::left << std::setw(10) << (iterator + 1) + << std::setw(15) << user->getId() + << std::setw(25) << user->getUserName() + << std::setw(25) << util::getUserTypeString(user->getUserType()) + << std::endl; + } + else + { + std::cout << "No users found.\n"; + util::pressEnter(); + return; + } + } +} + /* Function: selectServiceFromServices Description: Displays active services and allows the customer to select one by index. @@ -164,6 +222,11 @@ inline const Service* selectServiceFromServices(const util::MapgetState() != util::State::ACTIVE) { continue; @@ -285,3 +348,182 @@ inline bool getNotificationPreference(const std::string& serviceName) } } +/* +Function: filterActiveItems +Description: Filters out inactive inventory items and returns a map + containing only active items. +Parameter: const util::Map& inventoryItems - + map of all inventory items +Return type: util::Map +*/ +inline util::Map filterActiveItems(const util::Map& inventoryItems) +{ + util::Map activeItems; + int inventorySize = inventoryItems.getSize(); + for (int index = 0; index < inventorySize; index++) + { + const InventoryItem* item = inventoryItems.getValueAt(index); + if (item != nullptr && item->getState() != util::State::INACTIVE) + { + activeItems.insert(item->getId(), item); + } + } + return activeItems; +} + +/* +Function: displayInventoryWithItems +Description: Displays inventory items in a tabular format with index, ID, + part name, quantity, and price. +Parameter: util::Map& inventoryItems - + map of inventory items to display +Return type: void +*/ +inline void displayInventoryWithItems(util::Map& inventoryItems) +{ + int inventorySize = inventoryItems.getSize(); + std::cout << std::left << std::setw(10) << "Index" + << std::setw(15) << "Item ID" + << std::setw(25) << "Part Name" + << std::setw(10) << "Quantity" + << std::setw(10) << "Price" + << std::endl; + for (int iterator = 0; iterator < inventorySize; iterator++) + { + const InventoryItem* item = inventoryItems.getValueAt(iterator); + if (item != nullptr) + { + std::cout << std::left << std::setw(10) << (iterator + 1) + << std::setw(15) << item->getId() + << std::setw(25) << item->getPartName() + << std::setw(10) << item->getQuantity() + << std::setw(10) << item->getPrice() + << std::endl; + } + } +} + +/* +Function: addQuantityToItem +Description: Allows the admin to select an active inventory item and + increase its stock quantity. +Parameter: util::Map& inventoryItems - + map of inventory items + Controller& m_controller - controller instance to update stock +Return type: void +*/ +inline void addQuantityToItem(util::Map& inventoryItems, Controller& m_controller) +{ + int itemIndex; + int quantity; + auto activeItems = filterActiveItems(inventoryItems); + int activeSize = activeItems.getSize(); + if (activeSize == 0) + { + std::cout << "No active items available in Inventory" << std::endl; + return; + } + displayInventoryWithItems(activeItems); + std::cout << "Enter the index of the item to update: "; + util::read(itemIndex); + if (itemIndex < 1 || itemIndex > activeSize) + { + std::cout << "Invalid index selected." << std::endl; + return; + } + std::cout << "Enter quantity to add: "; + util::read(quantity); + if (quantity < 0) + { + std::cout << "The quantity should be Greater than 0." << std::endl; + return; + } + const InventoryItem* selectedItem = activeItems.getValueAt(itemIndex - 1); + if (selectedItem != nullptr) + { + std::string selectedItemId = selectedItem->getId(); + m_controller.addInventoryItemStock(selectedItemId, quantity); + std::cout << "Updated " << selectedItem->getPartName() + << " stock. New quantity: " << selectedItem->getQuantity() + << std::endl; + } + else + { + std::cout << "Error: Selected item could not be found." << std::endl; + } +} + +/* +Function: displayComboPackagesWithIndex +Description: Displays combo packages with index, ID, name, and discount percentage. +Parameter: util::Map& currentComboPackageIndexMap - combo packages map +Return type: void +*/ +inline void displayComboPackagesWithIndex(util::Map& currentComboPackageIndexMap) +{ + for (int iterator = 0; iterator < currentComboPackageIndexMap.getSize(); iterator++) + { + const ComboPackage* currentComboPackage = currentComboPackageIndexMap.getValueAt(iterator); + if (currentComboPackage == nullptr) + { + throw std::runtime_error("Error accessing the combopackage.\n"); + } + if (iterator == 0) + { + std::cout << std::left + << std::setw(8) << "Index" + << std::setw(10) << "ID" + << std::setw(20) << "Package Name" + << std::setw(15) << "Discount (%)" + << "\n"; + } + std::cout << std::left + << std::setw(8) << currentComboPackageIndexMap.getKeyAt(iterator) + << std::setw(10) << currentComboPackage->getId() + << std::setw(20) << currentComboPackage->getPackageName() + << std::setw(15) << currentComboPackage->getDiscountPercentage() + << "\n"; + } +} + +/* +Function: selectComboPackage +Description: Allows the admin to select an active combo package by index. +Parameter: util::Map& currentComboPackages - combo packages list +Return type: std::string - ID of the selected combo package +*/ +inline std::string selectComboPackage(util::Map& currentComboPackages) +{ + util::Map currentComboPackageIndexMap; + if (currentComboPackages.getSize() == 0) + { + throw std::runtime_error("No combo packages are available.\n"); + } + int currentIndex = 1, choice, selectedIndex; + for (int iterator = 0; iterator < currentComboPackages.getSize(); iterator++) + { + if (currentComboPackages.getValueAt(iterator)->getState() == util::State::INACTIVE) + { + continue; + } + currentComboPackageIndexMap.insert(currentIndex++, currentComboPackages.getValueAt(iterator)); + } + if (currentComboPackageIndexMap.getSize() == 0) + { + throw std::runtime_error("No combo packages currently active."); + } + displayComboPackagesWithIndex(currentComboPackageIndexMap); + std::cout << "Enter your choice(Index): "; + util::read(choice); + selectedIndex = currentComboPackageIndexMap.find(choice); + if (selectedIndex != -1) + { + std::string selectedComboPackageID = currentComboPackageIndexMap.getValueAt(selectedIndex)->getId(); + return selectedComboPackageID; + } + else + { + std::cout << "Enter a valid choice.\n"; + return ""; + } +} diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/TechnicianMenu.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/TechnicianMenu.cpp index ce1e5bc..3b66a90 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/TechnicianMenu.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/TechnicianMenu.cpp @@ -1,15 +1,16 @@ /* File: TechnicianMenu.cpp -Description: Implements the TechnicianMenu class which provides the technician’s console interface - in the Vehicle Service Management System. Handles menu display, user input, and - technician-specific operations such as completing jobs and viewing notifications. +Description: Implementation file containing the method definitions of the + TechnicianMenu class, including menu handling, job completion, + notification viewing, password management, and logout logic. Author: Trenser -Date: 19-May-2026 +Date:19-May-2026 */ - #include "TechnicianMenu.h" #include "InputHelper.h" #include "OutputHelper.h" +#include "Validator.h" +#include "MenuHelper.h" #include "MenuHelper.h" /* @@ -23,33 +24,62 @@ Returns: */ void TechnicianMenu::showMenu() { - bool isMenuActive = true; - while (isMenuActive) - { - try - { - int choice; - util::clear(); - std::cout << "" << std::endl; - util::read(choice); - if (!handleOperation(choice)) - { - isMenuActive = false; - } - } - catch (const std::exception& e) - { - std::cout << "Exception: " << e.what() << std::endl; - util::pressEnter(); - } - } + while (true) + { + try + { + int choice; + util::clear(); + std::cout << "Technician Menu" + << "\n1. Mark Job as Completed" + << "\n2. View Notifications" + << "\n3. Change Password" + << "\n4. Logout" + << "\nEnter a choice: "; + util::read(choice); + if (!handleOperation(choice)) + { + break; + } + } + catch (const std::exception& e) + { + std::cout << "Exception: " << e.what() << std::endl; + util::pressEnter(); + } + } } +/* +Function: handleOperation +Description: Executes the corresponding technician operation based on the selected menu choice. +Parameter: int choice - selected menu option +Return type: bool - true if menu continues, false if logout +*/ bool TechnicianMenu::handleOperation(int choice) { - return false; + switch (choice) + { + case 1: + completeJob(); + break; + case 2: + viewNotifications(); + break; + case 3: + changePassword(); + break; + case 4: + logout(); + return false; + default: + std::cout << "Enter a valid choice!" << std::endl; + util::pressEnter(); + } + return true; } + void TechnicianMenu::completeJob() { } @@ -66,3 +96,26 @@ void TechnicianMenu::viewNotifications() { viewAndDeleteNotification(m_controller); } + +/* +Function: logout +Description: Logs out the currently authenticated technician user. +Parameter: None +Return type: void +*/ +void TechnicianMenu::logout() +{ + m_controller.logout(); +} + +/* +Function: changePassword +Description: Allows the technician to change their password after validation. +Parameter: None +Return type: void +*/ + +void TechnicianMenu::changePassword() +{ + changePasswordHelper(m_controller); +} \ No newline at end of file diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/TechnicianMenu.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/TechnicianMenu.h index 3383362..3c7e9ed 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/TechnicianMenu.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/TechnicianMenu.h @@ -1,9 +1,10 @@ /* File: TechnicianMenu.h -Description: Declares the TechnicianMenu class which provides the technician-facing console menu in the Vehicle Service Management System. - Supports operations such as viewing assigned jobs, completing jobs, and managing notifications. +Description: Header file declaring the TechnicianMenu class, which provides + technician operations such as job completion, notification viewing, + password management, and logout functionality. Author: Trenser -Date: 19-May-2026 +Date:19-May-2026 */ #pragma once @@ -18,4 +19,6 @@ public: void showMenu(); void completeJob(); void viewNotifications(); + void logout(); + void changePassword(); }; diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/UserInterface.cpp b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/UserInterface.cpp index 04f240f..d1c48ba 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/UserInterface.cpp +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/UserInterface.cpp @@ -5,13 +5,13 @@ Description: Implementation file containing the method definitions of the and customer registration logic. Author: Trenser Date:19-May-2026 - */ -#include "UserInterface.h" + +#include "Enums.h" #include "InputHelper.h" #include "OutputHelper.h" -#include "Enums.h" #include "User.h" +#include "UserInterface.h" #include "Validator.h" /* diff --git a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/UserInterface.h b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/UserInterface.h index 52c2beb..501cfce 100644 --- a/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/UserInterface.h +++ b/Trenser.VehicleServiceSystem/Trenser.VehicleServiceSystem/views/UserInterface.h @@ -7,6 +7,7 @@ Description: Header file declaring the UserInterface class, which provides Author: Trenser Date:19-May-2026 */ + #pragma once #include "Controller.h" #include "AdminMenu.h"