diff --git a/carshop-service.iml b/carshop-service.iml
new file mode 100644
index 0000000..c90834f
--- /dev/null
+++ b/carshop-service.iml
@@ -0,0 +1,11 @@
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/pom.xml b/pom.xml
new file mode 100644
index 0000000..8d1999e
--- /dev/null
+++ b/pom.xml
@@ -0,0 +1,77 @@
+
+
+ 4.0.0
+
+ org.example
+ carshop
+ 1.0-SNAPSHOT
+
+
+ 17
+ 17
+ UTF-8
+ 5.10.0
+ 3.24.2
+ 4.8.1
+ 0.8.7
+ 1.18.30
+
+
+
+ org.junit.jupiter
+ junit-jupiter-api
+ ${jupiter.version}
+ test
+
+
+ org.junit.jupiter
+ junit-jupiter-engine
+ ${jupiter.version}
+ test
+
+
+ org.assertj
+ assertj-core
+ ${assertj.version}
+ test
+
+
+ org.mockito
+ mockito-core
+ ${mokito.version}
+ test
+
+
+ org.projectlombok
+ lombok
+ ${lombok.version}
+ provided
+
+
+
+
+
+
+ org.jacoco
+ jacoco-maven-plugin
+ ${jacoco.version}
+
+
+
+ prepare-agent
+
+
+
+ report
+ test
+
+ report
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/readme.md b/readme.md
index 4287ca8..c58139b 100644
--- a/readme.md
+++ b/readme.md
@@ -1 +1,23 @@
-#
\ No newline at end of file
+# Car Shop Management Application
+
+## Описание
+Это приложение предназначено для управления автосалоном
+
+## Взаимодействие с программой
+Интерфейс построен на вводе пользователем команд, предлагаемых для ввода программой в текущий момент времени
+1. Происходит регистрация/авторизация
+2. Отображение начального набора команд, в зависимости от роли пользователя
+3. Если роль администратор - CRUD автомобилей/заявок, создание/обновление данных о пользователях
+4. Если роль клиент - показ доступных для заказа автомобилей, показ заказов пользователя, формирование новых заказов
+
+# Краткое описание классов
+- Request - заказы на покупку, заявки на обслуживание
+- User - пользователи (Клиенты, Менеджеры, Администраторы)
+- Car - автомобили салона
+
++ CarShopService - управление коллекцией автомобилей
++ RequestService - управление коллекцией заказов
++ UserService - управление коллекцией пользователей
+
+* ConsoleUI - текстовое представление наборов команд
+* UserConsole - управление вводом пользователя
diff --git a/src/main/java/org/example/carshop/Main.java b/src/main/java/org/example/carshop/Main.java
new file mode 100644
index 0000000..3ccb704
--- /dev/null
+++ b/src/main/java/org/example/carshop/Main.java
@@ -0,0 +1,36 @@
+package org.example.carshop;
+
+import org.example.carshop.factory.RequestRepositoryFactory;
+import org.example.carshop.factory.CarRepositoryFactory;
+import org.example.carshop.factory.UserRepositoryFactory;
+import org.example.carshop.in.UserConsole;
+import org.example.carshop.factory.RequestServiceFactory;
+import org.example.carshop.factory.CarshopServiceFactory;
+import org.example.carshop.factory.CarshopFactory;
+import org.example.carshop.factory.UserConsoleFactory;
+import org.example.carshop.factory.UserServiceFactory;
+import org.example.carshop.repository.RequestRepository;
+import org.example.carshop.repository.CarRepository;
+import org.example.carshop.repository.UserRepository;
+import org.example.carshop.service.RequestService;
+import org.example.carshop.service.CarShopService;
+import org.example.carshop.service.UserService;
+
+public class Main {
+ public static void main(String[] args) {
+ CarshopFactory userRepositoryFactory = new UserRepositoryFactory();
+ CarshopFactory requestRepositoryFactory = new RequestRepositoryFactory();
+ CarshopFactory userServiceFactory = new UserServiceFactory(userRepositoryFactory);
+ CarshopFactory userConsoleFactory = getUserConsoleCarshopFactory(requestRepositoryFactory, userServiceFactory);
+
+ UserConsole userConsole = userConsoleFactory.create();
+ userConsole.runStartCommands();
+ }
+
+ private static CarshopFactory getUserConsoleCarshopFactory(CarshopFactory requestRepositoryFactory, CarshopFactory userServiceFactory) {
+ CarshopFactory carRepositoryFactory = new CarRepositoryFactory();
+ CarshopFactory carShopServiceFactory = new CarshopServiceFactory(carRepositoryFactory);
+ CarshopFactory requestServiceFactory = new RequestServiceFactory(requestRepositoryFactory);
+ return new UserConsoleFactory(userServiceFactory, carShopServiceFactory, requestServiceFactory);
+ }
+}
\ No newline at end of file
diff --git a/src/main/java/org/example/carshop/factory/CarRepositoryFactory.java b/src/main/java/org/example/carshop/factory/CarRepositoryFactory.java
new file mode 100644
index 0000000..26cb7b4
--- /dev/null
+++ b/src/main/java/org/example/carshop/factory/CarRepositoryFactory.java
@@ -0,0 +1,25 @@
+package org.example.carshop.factory;
+
+import org.example.carshop.model.Car;
+import org.example.carshop.repository.CarRepository;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Фабрика для создания объектов типа CarRepository.
+ * Реализует интерфейс CarshopFactory для создания экземпляров репозитория автомобилей.
+ */
+public class CarRepositoryFactory implements CarshopFactory {
+
+ /**
+ * Создает и возвращает новый экземпляр CarRepository с пустым начальным маппингом автомобилей.
+ *
+ * @return новый экземпляр CarRepository
+ */
+ @Override
+ public CarRepository create() {
+ Map carsHashMap = new HashMap<>();
+ return new CarRepository(carsHashMap);
+ }
+}
diff --git a/src/main/java/org/example/carshop/factory/CarshopFactory.java b/src/main/java/org/example/carshop/factory/CarshopFactory.java
new file mode 100644
index 0000000..83f20f7
--- /dev/null
+++ b/src/main/java/org/example/carshop/factory/CarshopFactory.java
@@ -0,0 +1,15 @@
+package org.example.carshop.factory;
+
+/**
+ * Интерфейс для общей фабрики, создающей экземпляры заданного типа.
+ * @param тип объекта, который будет создаваться фабрикой.
+ */
+public interface CarshopFactory {
+
+ /**
+ * Создает и возвращает новый экземпляр заданного типа.
+ *
+ * @return новый экземпляр заданного типа T.
+ */
+ T create();
+}
diff --git a/src/main/java/org/example/carshop/factory/CarshopServiceFactory.java b/src/main/java/org/example/carshop/factory/CarshopServiceFactory.java
new file mode 100644
index 0000000..88dc960
--- /dev/null
+++ b/src/main/java/org/example/carshop/factory/CarshopServiceFactory.java
@@ -0,0 +1,23 @@
+package org.example.carshop.factory;
+
+import lombok.RequiredArgsConstructor;
+import org.example.carshop.repository.CarRepository;
+import org.example.carshop.service.CarShopService;
+
+/**
+ * Фабрика для создания экземпляров {@link CarShopService}.
+ */
+@RequiredArgsConstructor
+public class CarshopServiceFactory implements CarshopFactory {
+ private final CarshopFactory carRepositoryFactory;
+
+ /**
+ * Создает и возвращает новый экземпляр {@link CarShopService}.
+ *
+ * @return новый экземпляр {@link CarShopService}.
+ */
+ @Override
+ public CarShopService create() {
+ return new CarShopService(carRepositoryFactory.create());
+ }
+}
diff --git a/src/main/java/org/example/carshop/factory/RequestRepositoryFactory.java b/src/main/java/org/example/carshop/factory/RequestRepositoryFactory.java
new file mode 100644
index 0000000..a4e0d89
--- /dev/null
+++ b/src/main/java/org/example/carshop/factory/RequestRepositoryFactory.java
@@ -0,0 +1,25 @@
+package org.example.carshop.factory;
+
+import org.example.carshop.model.Request;
+import org.example.carshop.repository.RequestRepository;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Фабрика для создания объектов типа RequestRepository.
+ * Реализует интерфейс CarshopFactory для создания экземпляров репозитория заказов.
+ */
+public class RequestRepositoryFactory implements CarshopFactory {
+
+ /**
+ * Создает и возвращает новый экземпляр RequestRepository.
+ *
+ * @return новый экземпляр RequestRepository
+ */
+ @Override
+ public RequestRepository create() {
+ Map requestHashMap = new HashMap<>();
+ return new RequestRepository(requestHashMap);
+ }
+}
diff --git a/src/main/java/org/example/carshop/factory/RequestServiceFactory.java b/src/main/java/org/example/carshop/factory/RequestServiceFactory.java
new file mode 100644
index 0000000..858d758
--- /dev/null
+++ b/src/main/java/org/example/carshop/factory/RequestServiceFactory.java
@@ -0,0 +1,25 @@
+package org.example.carshop.factory;
+
+import lombok.RequiredArgsConstructor;
+import org.example.carshop.repository.RequestRepository;
+import org.example.carshop.service.RequestService;
+
+/**
+ * Фабрика для создания объектов типа RequestService.
+ * Реализует интерфейс CarshopFactory для создания экземпляров сервиса заказов.
+ */
+@RequiredArgsConstructor
+public class RequestServiceFactory implements CarshopFactory {
+ private final CarshopFactory requestRepositoryFactory;
+
+ /**
+ * Создает и возвращает новый экземпляр RequestService, используя фабрику requestRepositoryFactory
+ * для создания необходимого RequestService.
+ *
+ * @return новый экземпляр RequestService
+ */
+ @Override
+ public RequestService create() {
+ return new RequestService(requestRepositoryFactory.create());
+ }
+}
diff --git a/src/main/java/org/example/carshop/factory/UserConsoleFactory.java b/src/main/java/org/example/carshop/factory/UserConsoleFactory.java
new file mode 100644
index 0000000..46b484f
--- /dev/null
+++ b/src/main/java/org/example/carshop/factory/UserConsoleFactory.java
@@ -0,0 +1,30 @@
+package org.example.carshop.factory;
+
+import lombok.RequiredArgsConstructor;
+import org.example.carshop.in.UserConsole;
+import org.example.carshop.service.RequestService;
+import org.example.carshop.service.CarShopService;
+import org.example.carshop.service.UserService;
+
+/**
+ * Фабрика для создания экземпляров {@link UserConsole}.
+ */
+@RequiredArgsConstructor
+public class UserConsoleFactory implements CarshopFactory {
+ private final CarshopFactory userServiceFactory;
+ private final CarshopFactory carShopServiceFactory;
+ private final CarshopFactory requestServiceFactory;
+
+ /**
+ * Создает и возвращает новый экземпляр {@link UserConsole}.
+ *
+ * @return новый экземпляр {@link UserConsole}.
+ */
+ @Override
+ public UserConsole create() {
+ UserService userService = userServiceFactory.create();
+ CarShopService carShopService = carShopServiceFactory.create();
+ RequestService requestService = requestServiceFactory.create();
+ return new UserConsole(userService, carShopService, requestService);
+ }
+}
diff --git a/src/main/java/org/example/carshop/factory/UserRepositoryFactory.java b/src/main/java/org/example/carshop/factory/UserRepositoryFactory.java
new file mode 100644
index 0000000..7114575
--- /dev/null
+++ b/src/main/java/org/example/carshop/factory/UserRepositoryFactory.java
@@ -0,0 +1,24 @@
+package org.example.carshop.factory;
+
+import org.example.carshop.model.User;
+import org.example.carshop.repository.UserRepository;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Фабрика для создания экземпляров {@link UserRepository}.
+ */
+public class UserRepositoryFactory implements CarshopFactory {
+
+ /**
+ * Создает и возвращает новый экземпляр {@link UserRepository}.
+ *
+ * @return новый экземпляр {@link UserRepository}.
+ */
+ @Override
+ public UserRepository create() {
+ Map userMap = new HashMap<>();
+ return new UserRepository(userMap);
+ }
+}
diff --git a/src/main/java/org/example/carshop/factory/UserServiceFactory.java b/src/main/java/org/example/carshop/factory/UserServiceFactory.java
new file mode 100644
index 0000000..6c1dd6c
--- /dev/null
+++ b/src/main/java/org/example/carshop/factory/UserServiceFactory.java
@@ -0,0 +1,23 @@
+package org.example.carshop.factory;
+
+import lombok.RequiredArgsConstructor;
+import org.example.carshop.repository.UserRepository;
+import org.example.carshop.service.UserService;
+
+/**
+ * Фабрика для создания экземпляров {@link UserService}.
+ */
+@RequiredArgsConstructor
+public class UserServiceFactory implements CarshopFactory {
+ private final CarshopFactory userRepositoryFactory;
+
+ /**
+ * Создает и возвращает новый экземпляр {@link UserService}.
+ *
+ * @return новый экземпляр {@link UserService}.
+ */
+ @Override
+ public UserService create() {
+ return new UserService(userRepositoryFactory.create());
+ }
+}
diff --git a/src/main/java/org/example/carshop/in/UserConsole.java b/src/main/java/org/example/carshop/in/UserConsole.java
new file mode 100644
index 0000000..53dcf91
--- /dev/null
+++ b/src/main/java/org/example/carshop/in/UserConsole.java
@@ -0,0 +1,667 @@
+package org.example.carshop.in;
+
+import org.example.carshop.model.enums.RequestStatus;
+import org.example.carshop.model.enums.RequestType;
+import org.example.carshop.model.enums.UserRole;
+import org.example.carshop.model.Request;
+import org.example.carshop.model.Car;
+import org.example.carshop.model.User;
+import org.example.carshop.out.ConsoleUI;
+import org.example.carshop.service.RequestService;
+import org.example.carshop.service.CarShopService;
+import org.example.carshop.service.UserService;
+
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.LocalTime;
+import java.time.format.DateTimeFormatter;
+import java.time.format.DateTimeParseException;
+import java.util.*;
+
+import static java.time.LocalDateTime.*;
+
+/**
+ * UserConsole processes user input and manages the logic for a car store management system.
+ * This class handles user registration, authorization, and navigation through various commands for users and administrators.
+ */
+public class UserConsole {
+ private UserService userService;
+ private CarShopService carShopService;
+ private RequestService requestService;
+ private Scanner in = new Scanner(System.in);
+ private User currentUser;
+ private boolean isAuthorized = false;
+
+ /**
+ * Constructs a UserConsole object with the necessary services.
+ *
+ * @param userService User service instance for managing user-related operations.
+ * @param carShopService Car service instance for managing car-related operations.
+ * @param requestService Request service instance for managing request-related operations.
+ */
+ public UserConsole(UserService userService, CarShopService carShopService, RequestService requestService) {
+ this.userService = userService;
+ this.carShopService = carShopService;
+ this.requestService = requestService;
+ }
+
+ /**
+ * Runs the initial commands loop of the console application.
+ * Handles user registration, authorization, and main menu navigation based on user roles.
+ */
+ public void runStartCommands() {
+ while (true) {
+ try {
+
+ if (isAuthorized) {
+ switch (currentUser.getRole()) {
+ case ADMIN -> runCarShopAdminCommands();
+ case CLIENT -> runCarShopClientCommands();
+ case MANAGER -> runCarShopManagerCommands();
+ }
+ }
+
+ ConsoleUI.printStartCommands();
+
+ int command = in.nextInt();
+ in.nextLine();
+
+ switch (command) {
+ case 1 -> registration();
+ case 2 -> authorization();
+ case 3 -> {
+ in.close();
+ return;
+ }
+ default -> System.out.println("Неверная команда");
+ }
+
+ } catch (InputMismatchException inputMismatchException) {
+ System.out.println("Неверный формат ввода команды. Введите корректные данные");
+ in.next();
+ } catch (DateTimeParseException dateTimeParseException) {
+ System.out.println("Некорректный формат ввода данных бронирования. Введите корректные данные");
+ }
+ }
+ }
+
+ /**
+ * Handles the user registration process.
+ * Prompts the user for username, password, and role selection to create a new user account.
+ */
+ private void registration() {
+ System.out.print("Введите имя пользователя: ");
+ String username = in.nextLine();
+ User user = userService.findUserByName(username);
+
+ if (user != null) {
+ System.out.println("Пользователь с таким username уже существует!");
+ return;
+ }
+
+ System.out.print("Введите пароль: ");
+ String password = in.nextLine();
+
+ System.out.print("Введите ФИО: ");
+ String fullName = in.nextLine();
+
+ ConsoleUI.printUserRoles();
+ int userRole = in.nextInt();
+ in.nextLine();
+
+ switch (userRole) {
+ case 1 -> userService.register(new User(username, password, fullName, UserRole.CLIENT));
+ case 2 -> userService.register(new User(username, password, fullName, UserRole.ADMIN));
+ case 3 -> userService.register(new User(username, password, fullName, UserRole.MANAGER));
+ default -> {
+ System.out.println("Введена неверная комманда!");
+ return;
+ }
+ }
+ System.out.println("Регистрация прошла успешна!");
+ }
+
+ /**
+ * Handles the user authorization process.
+ * Prompts the user for username and password to authenticate and log in to the system.
+ */
+ private void authorization() {
+ System.out.print("Введите имя пользователя: ");
+ String username = in.nextLine();
+ System.out.print("Введите пароль: ");
+ String password = in.nextLine();
+
+ User user = new User(username, password);
+ if (userService.findUserByName(username) == null) {
+ System.out.println("Пользователя с таким именем не существует!");
+ return;
+ }
+
+ boolean success = userService.login(user);
+ if (success) {
+ System.out.println("Авторизация прошла успешно.");
+ currentUser = userService.findUserByName(username);
+ isAuthorized = true;
+ } else {
+ System.out.println("Неверное имя пользователя или пароль.");
+ }
+ }
+
+ /**
+ * Runs the commands loop for administrative operations in the Car Shop.
+ */
+ public void runCarShopAdminCommands() {
+ while (isAuthorized) {
+
+ ConsoleUI.printCarShopAdminCommands();
+
+ int command = in.nextInt();
+ in.nextLine();
+ switch (command) {
+ case 1 -> runCarCommands();
+ case 2 -> runRequestCommands();
+ case 3 -> runUsersCommands();
+ case 4 -> {
+ isAuthorized = false;
+ currentUser = null;
+ return;
+ }
+ default -> System.out.println("Неверная команда");
+ }
+ }
+ }
+
+ /**
+ * Runs the commands loop for customer operations.
+ * Provides options for viewing cars available for purchase, customer purchase requests,
+ * and options for creating new purchase requests.
+ */
+ public void runCarShopClientCommands() {
+ while (isAuthorized) {
+
+ ConsoleUI.printCarShopClientCommands();
+
+ int command = in.nextInt();
+ in.nextLine();
+
+ switch (command) {
+ case 1 -> printCollection(carShopService.searchCars(null, null, null, true));
+ case 2 -> printCollection(requestService.filterRequestsByUserAndType(currentUser, null));
+ case 3 -> {
+ System.out.print("Введите ID автомобиля: ");
+ int carId = in.nextInt();
+ in.nextLine();
+ Car car = carShopService.findCarById(carId);
+ if (car != null && !car.isAvailable()) {
+ System.out.println("Автомобиль не доступен к заказу");
+ continue;
+ } else if (car == null) {
+ System.out.println("Автомобиль с таким ID не существует");
+ continue;
+ }
+ requestService.addRequest(new Request(currentUser, carId, now(), null, RequestType.ORDER, RequestStatus.NEW));
+ car.setAvailable(false);
+ System.out.print("Заказ успешно добавлен!");
+ }
+ case 4 -> {
+ isAuthorized = false;
+ currentUser = null;
+ }
+ default -> System.out.println("Неверная команда");
+ }
+
+ }
+ }
+
+ /**
+ * Runs the commands loop for Manager operations.
+ * Provides options for searching cars, requests management, viewing users info.
+ */
+ public void runCarShopManagerCommands() {
+ while (isAuthorized) {
+
+ ConsoleUI.printCarShopManagerCommands();
+
+ int command = in.nextInt();
+ in.nextLine();
+
+ switch (command) {
+ case 1 -> {
+ System.out.print("Введите название модели: ");
+ String modelName = in.nextLine();
+
+ System.out.print("Введите название производителя: ");
+ String brandName = in.nextLine();
+
+ System.out.print("Введите год производства: ");
+ String prodYear = in.nextLine();
+
+ printCollection(carShopService.searchCars(brandName, modelName, prodYear, null));
+
+ }
+ case 2 -> runRequestCommands();
+ case 3 -> runUsersCommands();
+ case 4 -> {
+ isAuthorized = false;
+ currentUser = null;
+ }
+ default -> System.out.println("Неверная команда");
+ }
+
+ }
+ }
+
+ /**
+ * Runs the commands loop for managing Car operations.
+ * Includes options for adding, updating, deleting cars.
+ */
+ public void runCarCommands() {
+ while (true) {
+ ConsoleUI.printCarCommands();
+
+ int command = in.nextInt();
+ in.nextLine();
+
+ switch (command) {
+ case 1 -> {
+ System.out.println("Добавление автомобиля");
+ System.out.print("Введите идентификатор:");
+ int id = in.nextInt();
+ in.nextLine();
+ Car car = carShopService.findCarById(id);
+
+ if (car != null) {
+ System.out.println("Автомобиль с таким ID уже существует!");
+ continue;
+ }
+
+ System.out.print("Введите название модели: ");
+ String modelName = in.nextLine();
+
+ System.out.print("Введите название производителя: ");
+ String brandName = in.nextLine();
+
+ System.out.print("Введите год производства: ");
+ String prodYear = in.nextLine();
+
+ System.out.print("Введите описание текущего состояния: ");
+ String stateDesc = in.nextLine();
+
+ carShopService.addCar(new Car(id, modelName, brandName, prodYear, stateDesc, true));
+ }
+ case 2 -> {
+ System.out.println("Изменение данных об автомобиле");
+ System.out.print("Введите идентификатор: ");
+ int id = in.nextInt();
+ in.nextLine();
+ Car car = carShopService.findCarById(id);
+
+ if (car == null) {
+ System.out.println("Автомобиль с таким ID не существует!");
+ continue;
+ }
+
+ System.out.print("Введите название модели: ");
+ String modelName = in.nextLine();
+
+ System.out.print("Введите название производителя: ");
+ String brandName = in.nextLine();
+
+ System.out.print("Введите год производства: ");
+ String prodYear = in.nextLine();
+
+ System.out.print("Введите описание текущего состояния: ");
+ String stateDesc = in.nextLine();
+
+ ConsoleUI.printAvailabilityCommands();
+ int availableChoice = in.nextInt();
+ in.nextLine();
+
+ boolean isAvailable;
+ switch (availableChoice) {
+ case 1 -> isAvailable = false;
+ case 2 -> isAvailable = true;
+ default -> {
+ System.out.println("Произошла ошибка");
+ continue;
+ }
+ }
+
+ Car updatedCar = new Car(id, modelName, brandName, prodYear, stateDesc, isAvailable);
+ carShopService.updateCar(updatedCar);
+ }
+ case 3 -> {
+ System.out.println("Удаление автомобиля");
+ System.out.print("Введите идентификатор: ");
+ int id = in.nextInt();
+ in.nextLine();
+
+ Car car = carShopService.findCarById(id);
+
+ if (car != null) {
+ System.out.println("Автомобиль с таким ID не существует!");
+ continue;
+ }
+
+ carShopService.deleteCar(id);
+ }
+ case 4 -> printCollection(carShopService.getAllCars());
+ case 5 -> {
+ return;
+ }
+
+ default -> System.out.println("Неверная команда");
+ }
+ }
+ }
+
+ /**
+ * Runs the commands loop for managing Car Shop employees and clients.
+ * Includes options for adding, updating, retrieving users.
+ */
+ public void runUsersCommands() {
+ while (true) {
+ ConsoleUI.printUsersCommands();
+
+ int command = in.nextInt();
+ in.nextLine();
+
+ switch (command) {
+ case 1 -> printCollection(userService.searchUsers(null, List.of(UserRole.CLIENT)));
+ case 2 -> printCollection(userService.searchUsers(null, Arrays.asList(UserRole.MANAGER, UserRole.ADMIN)));
+ case 3 -> {
+ System.out.print("Введите имя пользователя: ");
+ String userName = in.nextLine();
+
+ ConsoleUI.printUserRoles();
+ UserRole userRole = UserRole.CLIENT;
+ int requestTypeIn = in.nextInt();
+ in.nextLine();
+ switch (requestTypeIn) {
+ case 1 -> {
+ }
+ case 2 -> userRole = UserRole.ADMIN;
+ case 3 -> userRole = UserRole.MANAGER;
+ default -> System.out.println("Введена несуществующая команда!");
+ }
+ printCollection(userService.searchUsers(userName,List.of(userRole)));
+ }
+ case 4 -> registration();
+ case 5 ->{
+ System.out.print("Введите username пользователя: ");
+ String username = in.nextLine();
+ User user = userService.findUserByName(username);
+ if (user == null) {
+ System.out.println("Пользователя с таким именем не существует!");
+ continue;
+ }
+
+ System.out.print("Введите новое ФИО пользователя: ");
+ String fullName = in.nextLine();
+
+ System.out.print("Введите новый пароль пользователя: ");
+ String password = in.nextLine();
+
+ ConsoleUI.printUserRoles();
+ UserRole userRole = UserRole.CLIENT;
+ int requestTypeIn = in.nextInt();
+ in.nextLine();
+ switch (requestTypeIn) {
+ case 1 -> {}
+ case 2 -> userRole = UserRole.ADMIN;
+ case 3 -> userRole = UserRole.MANAGER;
+ default -> System.out.println("Введена несуществующая команда!");
+ }
+
+ User updatedUser = new User(username, password, fullName, userRole);
+ userService.updateUser(updatedUser);
+ }
+ case 6 -> {return;}
+ default -> System.out.println("Неверная команда");
+ }
+ }
+ }
+
+ /**
+ * Prompts the user to input request date and time.
+ *
+ * @return An array of LocalDateTime objects representing creation and completion date/time of request.
+ */
+ public LocalDateTime[] RequestDateTimeInput() {
+ DateTimeFormatter dateFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
+ DateTimeFormatter timeFormatter = DateTimeFormatter.ofPattern("HH:mm");
+
+ System.out.println("Введите значение даты создания заказа (в формате YYYY-MM-DD):");
+ String startDate = in.nextLine();
+ LocalDate startLocalDate = LocalDate.parse(startDate, dateFormatter);
+
+ System.out.println("Введите значение времени создания заказа (в формате HH:MM):");
+ String startTime = in.nextLine();
+ LocalTime startLocalTime = LocalTime.parse(startTime, timeFormatter);
+
+ LocalDateTime startDateTime = of(startLocalDate, startLocalTime);
+
+ System.out.println("Введите значение даты выполнения заказа (в формате YYYY-MM-DD):");
+ String endDate = in.nextLine();
+ LocalDate endLocalDate = LocalDate.parse(endDate, dateFormatter);
+
+ System.out.println("Введите значение времени выполнения заказа (в формате HH:MM):");
+ String endTime = in.nextLine();
+ LocalTime endLocalTime = LocalTime.parse(endTime, timeFormatter);
+
+ LocalDateTime endDateTime = of(endLocalDate, endLocalTime);
+
+ if (startDateTime.isAfter(endDateTime)) {
+ System.out.println("Дата конца бронирования не может идти раньше начала!");
+ return null;
+ }
+ return new LocalDateTime[]{startDateTime, endDateTime};
+ }
+
+ /**
+ * Runs the commands loop for managing requests.
+ * Provides options for viewing, filtering, creating, and canceling request for car order and maintenance.
+ */
+ public void runRequestCommands() {
+ while (true) {
+ ConsoleUI.printRequestCommands();
+
+ int command = in.nextInt();
+ in.nextLine();
+
+ switch (command) {
+ case 1 -> printCollection(requestService.getAllRequests());
+ case 2 -> {
+ ConsoleUI.printRequestTypes();
+ RequestType requestType = RequestType.ORDER;
+ int requestTypeIn = in.nextInt();
+ in.nextLine();
+
+ switch (requestTypeIn) {
+ case 1 -> {
+ }
+ case 2 -> requestType = RequestType.MAINTENANCE;
+ default -> System.out.println("Введена несуществующая команда!");
+ }
+
+ ConsoleUI.printRequestFilterCommands();
+ int filterKindIn = in.nextInt();
+ in.nextLine();
+
+ switch (filterKindIn) {
+ case 1 -> {
+ DateTimeFormatter dateFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
+ System.out.println("Введите дату для фильтрации заказов (в формате YYYY-MM-DD):");
+ String startDate = in.nextLine();
+ LocalDate startLocalDate = LocalDate.parse(startDate, dateFormatter);
+ printCollection(requestService.filterRequestsByDateAndType(startLocalDate, requestType));
+ }
+ case 2 -> {
+ System.out.print("Введите имя пользователя для фильтрации заказов: ");
+ String username = in.nextLine();
+ User filterUser = userService.findUserByName(username);
+ if (filterUser != null) {
+ printCollection(requestService.filterRequestsByUserAndType(filterUser, requestType));
+ } else {
+ System.out.println("Пользователь с таким username не найден!");
+ }
+ }
+ case 3 -> {
+ System.out.print("Выберите статус для фильтрации заказов: ");
+ ConsoleUI.printRequestStatuses();
+ RequestStatus requestStatus = RequestStatus.NEW;
+ int requestStatusIn = in.nextInt();
+ in.nextLine();
+ switch (requestStatusIn) {
+ case 1 -> {}
+ case 2 -> requestStatus = RequestStatus.PENDING;
+ case 3 -> requestStatus = RequestStatus.IN_PROGRESS;
+ case 4 -> requestStatus = RequestStatus.COMPLETED;
+ default -> System.out.println("Введена несуществующая команда!");
+ }
+ printCollection(requestService.filterRequestsByRequestStatusAndType(requestStatus, requestType));
+ }
+ case 4 -> {
+ System.out.print("Введите идентификатор автомобиля для фильтрации заказов: ");
+ int carId = in.nextInt();
+ in.nextLine();
+ Car car = carShopService.findCarById(carId);
+ if (car != null) {
+ printCollection(requestService.filterRequestsByCarAndType(carId, requestType));
+ } else {
+ System.out.println("Автомобиль с таким ID не найден!");
+ }
+ }
+ case 5 -> {
+ return;
+ }
+ default -> System.out.println("Введена несуществующая команда!");
+ }
+ }
+ case 3 -> {
+ System.out.print("Введите ID автомобиля: ");
+ int carId = in.nextInt();
+ in.nextLine();
+ Car car = carShopService.findCarById(carId);
+ if (car != null && !car.isAvailable()) {
+ System.out.println("Автомобиль не доступен к заказу");
+ continue;
+ } else if (car == null) {
+ System.out.println("Автомобиль с таким ID не существует");
+ continue;
+ }
+ requestService.addRequest(new Request(currentUser, carId, now(), null, RequestType.ORDER, RequestStatus.NEW));
+ car.setAvailable(false);
+ System.out.print("Заказ успешно добавлен!");
+ }
+ case 4 -> {
+ System.out.print("Введите идентификатор: ");
+ int id = in.nextInt();
+ in.nextLine();
+ Request foundRequest = requestService.findRequestById(id);
+
+ if (foundRequest != null) {
+ requestService.deleteRequest(id);
+ } else {
+ System.out.println("Заказ с таким ID не существует!");
+ }
+ }
+ case 5 -> {
+ System.out.print("Введите идентификатор: ");
+ int id = in.nextInt();
+ in.nextLine();
+ Request foundRequest = requestService.findRequestById(id);
+
+ if (foundRequest != null) {
+ System.out.print("Выберите статус: ");
+ ConsoleUI.printRequestStatuses();
+ RequestStatus requestStatus = RequestStatus.NEW;
+ int requestStatusIn = in.nextInt();
+ in.nextLine();
+ switch (requestStatusIn) {
+ case 1 -> {}
+ case 2 -> requestStatus = RequestStatus.PENDING;
+ case 3 -> requestStatus = RequestStatus.IN_PROGRESS;
+ case 4 -> requestStatus = RequestStatus.COMPLETED;
+ default -> System.out.println("Введена несуществующая команда!");
+ }
+ foundRequest.changeStatus(requestStatus);
+ } else {
+ System.out.println("Заказ с таким ID не существует!");
+ }
+ }
+ case 6 -> {
+ System.out.print("Введите идентификатор: ");
+ int id = in.nextInt();
+ in.nextLine();
+ Request foundRequest = requestService.findRequestById(id);
+ if (foundRequest == null) {
+ System.out.println("Заказа с таким ID не существует!");
+ continue;
+ }
+
+ System.out.print("Введите username пользователя: ");
+ String username = in.nextLine();
+ User user = userService.findUserByName(username);
+ if (user == null) {
+ System.out.println("Пользователя с таким именем не существует!");
+ continue;
+ }
+
+ System.out.print("Введите ID автомобиля: ");
+ int carId = in.nextInt();
+ in.nextLine();
+ Car car = carShopService.findCarById(carId);
+ if (car == null) {
+ System.out.println("Автомобиль с таким ID не существует");
+ continue;
+ }
+
+ LocalDateTime[] requestDateTimes = RequestDateTimeInput();
+
+ ConsoleUI.printRequestTypes();
+ RequestType requestType = RequestType.ORDER;
+ int requestTypeIn = in.nextInt();
+ in.nextLine();
+ switch (requestTypeIn) {
+ case 1 -> {}
+ case 2 -> requestType = RequestType.MAINTENANCE;
+ default -> System.out.println("Введена несуществующая команда!");
+ }
+
+ System.out.print("Выберите статус: ");
+ ConsoleUI.printRequestStatuses();
+ RequestStatus requestStatus = RequestStatus.NEW;
+ int requestStatusIn = in.nextInt();
+ in.nextLine();
+
+ switch (requestStatusIn) {
+ case 1 -> {}
+ case 2 -> requestStatus = RequestStatus.PENDING;
+ case 3 -> requestStatus = RequestStatus.IN_PROGRESS;
+ case 4 -> requestStatus = RequestStatus.COMPLETED;
+ default -> System.out.println("Введена несуществующая команда!");
+ }
+ requestService.addRequest(new Request(user, carId, requestDateTimes[0], requestDateTimes[1], requestType, requestStatus));
+ }
+ case 7 -> {
+ isAuthorized = false;
+ currentUser = null;
+ return;
+ }
+ default -> System.out.println("Неверная команда");
+ }
+ }
+ }
+
+ /**
+ * Prints the elements of an ArrayList to the console.
+ *
+ * @param collection The Collection containing elements to print.
+ */
+ public void printCollection(Collection> collection) {
+ for (Object object : collection) {
+ System.out.println(object);
+ }
+ }
+}
diff --git a/src/main/java/org/example/carshop/model/Car.java b/src/main/java/org/example/carshop/model/Car.java
new file mode 100644
index 0000000..11855b4
--- /dev/null
+++ b/src/main/java/org/example/carshop/model/Car.java
@@ -0,0 +1,42 @@
+package org.example.carshop.model;
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+
+/**
+ * Represents a car for purchase in the Car Shop.
+ */
+@Data
+@AllArgsConstructor
+public class Car {
+ /**
+ * Unique identifier for the car model.
+ */
+ private int id;
+
+ /**
+ * The name of the model.
+ */
+ private String modelName;
+
+ /**
+ * The name of the car brand.
+ */
+ private String brandName;
+
+ /**
+ * The year the car was produced in.
+ */
+ private String prodYear;
+
+ /**
+ * The description of current car state.
+ */
+ private String stateDesc;
+
+ /**
+ * Indicates whether the car is currently available for order.
+ */
+ private boolean isAvailable;
+
+}
diff --git a/src/main/java/org/example/carshop/model/Request.java b/src/main/java/org/example/carshop/model/Request.java
new file mode 100644
index 0000000..9a107e4
--- /dev/null
+++ b/src/main/java/org/example/carshop/model/Request.java
@@ -0,0 +1,85 @@
+package org.example.carshop.model;
+
+import lombok.Data;
+import org.example.carshop.model.enums.RequestStatus;
+import org.example.carshop.model.enums.RequestType;
+
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.LocalTime;
+
+/**
+ * Represents a customer's request for a new car or a car maintenance.
+ * Each request is uniquely identified by an id which is auto-incremented.
+ */
+@Data
+public class Request {
+ private static int nextRequestId = 1;
+
+ /**
+ * Unique identifier for the request.
+ */
+ private int id;
+
+ /**
+ * The user who made the request.
+ */
+ private User user;
+
+ /**
+ * The id of the car being booked.
+ */
+ private int carId;
+
+ /**
+ * The creation time of the request.
+ */
+ private LocalDateTime creationTime;
+
+ /**
+ * The completion time of the request.
+ */
+ private LocalDateTime completionTime;
+
+ /**
+ * The type of the resource being booked.
+ */
+ private RequestType requestType;
+
+ /**
+ * The type of current status of the request.
+ */
+ private RequestStatus requestStatus;
+
+ /**
+ * Constructs a new Request with the given parameters.
+ * The id is auto-generated and incremented.
+ *
+ * @param user the user who made the request
+ * @param carId the id of the User's car
+ * @param creationTime the creation time of the request
+ * @param requestType the type of the resource being requested
+ * @param requestStatus type of current status of the request
+ */
+ public Request(User user, int carId, LocalDateTime creationTime,
+ LocalDateTime completionTime, RequestType requestType, RequestStatus requestStatus) {
+ this.id = nextRequestId++;
+ this.user = user;
+ this.carId = carId;
+ this.creationTime = creationTime != null ? creationTime : LocalDateTime.now();
+ this.completionTime = completionTime != null ? completionTime : LocalDateTime.of(1970, 1, 1, 1, 1, 1);
+ this.requestType = requestType;
+ this.requestStatus = RequestStatus.NEW;
+ }
+
+
+ /**
+ * Changes the status of the request.
+ *
+ * @param newStatus The new status to set for the request.
+ */
+ public void changeStatus(RequestStatus newStatus) {
+ this.requestStatus = newStatus;
+ }
+}
+
diff --git a/src/main/java/org/example/carshop/model/User.java b/src/main/java/org/example/carshop/model/User.java
new file mode 100644
index 0000000..4ec9fb4
--- /dev/null
+++ b/src/main/java/org/example/carshop/model/User.java
@@ -0,0 +1,51 @@
+package org.example.carshop.model;
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import org.example.carshop.model.enums.UserRole;
+
+/**
+ * Represents a user in the Car Shop system.
+ */
+@Data
+@AllArgsConstructor
+public class User {
+ /**
+ * The username of the user.
+ */
+ private String username;
+
+ /**
+ * The password of the user.
+ */
+ private String password;
+
+ /**
+ * The credentials of the user.
+ */
+ private String fullName;
+
+ /**
+ * The role of the user.
+ */
+ private UserRole role = UserRole.CLIENT;
+
+ /**
+ * Manual constructor that only requires username and password, allowing other fields to be null.
+ */
+ public User(String username, String password) {
+ this(username, password, null, null);
+ }
+ /**
+ * Returns a string representation of the user.
+ *
+ * @return A string representing the user, excluding the password.
+ */
+ @Override
+ public String toString() {
+ return "User{" +
+ "username='" + username + '\'' +
+ ", role=" + role +
+ '}';
+ }
+}
diff --git a/src/main/java/org/example/carshop/model/enums/RequestStatus.java b/src/main/java/org/example/carshop/model/enums/RequestStatus.java
new file mode 100644
index 0000000..571037d
--- /dev/null
+++ b/src/main/java/org/example/carshop/model/enums/RequestStatus.java
@@ -0,0 +1,8 @@
+package org.example.carshop.model.enums;
+
+public enum RequestStatus {
+ NEW,
+ PENDING,
+ IN_PROGRESS,
+ COMPLETED
+}
diff --git a/src/main/java/org/example/carshop/model/enums/RequestType.java b/src/main/java/org/example/carshop/model/enums/RequestType.java
new file mode 100644
index 0000000..e7be0a8
--- /dev/null
+++ b/src/main/java/org/example/carshop/model/enums/RequestType.java
@@ -0,0 +1,6 @@
+package org.example.carshop.model.enums;
+
+public enum RequestType {
+ ORDER,
+ MAINTENANCE
+}
diff --git a/src/main/java/org/example/carshop/model/enums/UserRole.java b/src/main/java/org/example/carshop/model/enums/UserRole.java
new file mode 100644
index 0000000..50278e3
--- /dev/null
+++ b/src/main/java/org/example/carshop/model/enums/UserRole.java
@@ -0,0 +1,7 @@
+package org.example.carshop.model.enums;
+
+public enum UserRole {
+ CLIENT,
+ ADMIN,
+ MANAGER
+}
diff --git a/src/main/java/org/example/carshop/out/ConsoleUI.java b/src/main/java/org/example/carshop/out/ConsoleUI.java
new file mode 100644
index 0000000..30a979c
--- /dev/null
+++ b/src/main/java/org/example/carshop/out/ConsoleUI.java
@@ -0,0 +1,164 @@
+package org.example.carshop.out;
+
+/**
+ * The {@code ConsoleUI} class provides static methods for printing various command menus to the console.
+ * These methods are used to display different options to the user in a console-based Car Shop management application.
+ */
+public class ConsoleUI {
+
+ /**
+ * Prints the start commands menu.
+ */
+ public static void printStartCommands() {
+ System.out.print("""
+ Выберите команду:
+ 1 - Регистрация
+ 2 - Авторизация
+ 3 - Выход
+ """);
+ }
+
+ /**
+ * Prints the Car Shop Client commands menu.
+ */
+ public static void printCarShopClientCommands() {
+ System.out.print("""
+ Выберите команду:
+ 1 - Показать доступные для заказа автомобили
+ 2 - Показать заказы пользователя
+ 3 - Новый заказ
+ 4 - Выход из пользователя
+ """);
+ }
+
+ /**
+ * Prints the Car Shop Manager commands menu.
+ */
+ public static void printCarShopManagerCommands() {
+ System.out.print("""
+ Выберите команду:
+ 1 - Поиск автомобиля
+ 2 - Обработка заказов
+ 3 - Просмотр информации о клиентах и сотрудниках
+ 4 - Выход из пользователя
+ """);
+ }
+
+ /**
+ * Prints the Car Shop Admin commands menu.
+ */
+ public static void printCarShopAdminCommands() {
+ System.out.print("""
+ Выберите команду:
+ 1 - Управление автомобилями
+ 2 - Обработка заказов
+ 3 - Просмотр информации о клиентах и сотрудниках
+ 4 - Выход из пользователя
+ """);
+ }
+
+ /**
+ * Prints the cars management commands menu.
+ */
+ public static void printCarCommands() {
+ System.out.print("""
+ Выберите команду для управления автомобилями:
+ 1 - Добавить
+ 2 - Изменить данные
+ 3 - Удалить
+ 4 - Показать все
+ 5 - Вернуться назад
+ """);
+ }
+
+ /**
+ * Prints the users management commands menu.
+ */
+ public static void printUsersCommands() {
+ System.out.print("""
+ Выберите команду для управления и просмотра информации о клиентах и сотрудниках:
+ 1 - Просмотр списка зарегистрированных клиентов
+ 2 - Просмотр списка зарегистрированных сотрудников
+ 3 - Поиск по критериям
+ 4 - Добавить пользователя
+ 5 - Изменить данные пользователя
+ 6 - Вернуться назад
+ """);
+ }
+
+ /**
+ * Prints the car availability commands menu.
+ */
+ public static void printAvailabilityCommands() {
+ System.out.print("""
+ Произведен ли заказ автомобиля?
+ 1 - Да
+ 2 - Нет
+ """);
+ }
+
+ /**
+ * Prints the request commands menu.
+ */
+ public static void printRequestCommands() {
+ System.out.print("""
+ Выберите команду для обработки заказов:
+ 1 - Показать все заказы
+ 2 - Поиск заказа
+ 3 - Новый заказ
+ 4 - Отменить заказ
+ 5 - Изменить статус заказа
+ 6 - Изменить данные заказа
+ 7 - Вернуться назад
+ """);
+ }
+
+ /**
+ * Prints the request filter commands menu.
+ */
+ public static void printRequestFilterCommands() {
+ System.out.print("""
+ Выберите фильтр:
+ 1 - Поиск по дате
+ 2 - Поиск по клиенту
+ 3 - Поиск по статусу
+ 4 - Поиск по автомобилю
+ 5 - Вернуться назад
+ """);
+ }
+
+ /**
+ * Prints the request types commands menu.
+ */
+ public static void printRequestTypes() {
+ System.out.print("""
+ Выберите тип заказа:
+ 1 - Заказ на покупку автомобиля
+ 2 - Заявка на обслуживание автомобиля
+ """);
+ }
+ /**
+ * Prints the request statuses commands menu.
+ */
+ public static void printRequestStatuses() {
+ System.out.print("""
+ Выберите статус:
+ 1 - Новый
+ 2 - В ожидании
+ 3 - В работе
+ 4 - Завершен
+ """);
+ }
+
+ /**
+ * Prints the user roles commands menu.
+ */
+ public static void printUserRoles() {
+ System.out.print("""
+ Выберите роль
+ 1 - Клиент
+ 2 - Администратор
+ 3 - Менеджер
+ """);
+ }
+}
diff --git a/src/main/java/org/example/carshop/repository/CarRepository.java b/src/main/java/org/example/carshop/repository/CarRepository.java
new file mode 100644
index 0000000..2e28ff3
--- /dev/null
+++ b/src/main/java/org/example/carshop/repository/CarRepository.java
@@ -0,0 +1,79 @@
+package org.example.carshop.repository;
+
+import lombok.AllArgsConstructor;
+import org.example.carshop.model.Car;
+import java.util.Collection;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+/**
+ * Repository class for managing ConferenceHall entities.
+ */
+@AllArgsConstructor
+public class CarRepository {
+ private final Map carsMap;
+
+ /**
+ * Retrieves all cars in Car Shop.
+ *
+ * @return a collection of all cars.
+ */
+ public Collection getAllCars() {
+ return carsMap.values();
+ }
+
+ /**
+ * Adds a new car to the repository.
+ *
+ * @param car the car entity to add.
+ */
+ public void addCar(Car car) {
+ carsMap.put(car.getId(), car);
+ }
+
+ /**
+ * Removes a car from the repository by its ID.
+ *
+ * @param carId the ID of the conference hall to remove.
+ */
+ public void removeCarById(int carId) {
+ carsMap.remove(carId);
+ }
+
+ /**
+ * Finds a car by its ID.
+ *
+ * @param carId the ID of the car to find.
+ * @return the car object with the specified ID, or null if not found.
+ */
+ public Car findCarById(int carId) {
+ return carsMap.get(carId);
+ }
+
+ /**
+ * Updates an existing car in the repository.
+ *
+ * @param car the car object with updated information.
+ */
+ public void updateCar(Car car) {
+ carsMap.put(car.getId(), car);
+ }
+
+ /**
+ * Filters cars based on given parameters.
+ *
+ * @param brand Filter by brand.
+ * @param model Filter by model.
+ * @param prodYear Filter by year of manufacture.
+
+ * @return Filtered collection of cars.
+ */
+ public Collection filterCars(String brand, String model, String prodYear, Boolean isAvailable) {
+ return carsMap.values().stream()
+ .filter(car -> (brand == null || car.getBrandName().equals(brand))
+ && (model == null || car.getModelName().equals(model))
+ && (prodYear == null || car.getProdYear().equals(prodYear))
+ && (isAvailable == null || car.isAvailable() == isAvailable))
+ .collect(Collectors.toList());
+ }
+}
diff --git a/src/main/java/org/example/carshop/repository/RequestRepository.java b/src/main/java/org/example/carshop/repository/RequestRepository.java
new file mode 100644
index 0000000..f8cd83f
--- /dev/null
+++ b/src/main/java/org/example/carshop/repository/RequestRepository.java
@@ -0,0 +1,120 @@
+package org.example.carshop.repository;
+
+import lombok.AllArgsConstructor;
+import org.example.carshop.model.Car;
+import org.example.carshop.model.Request;
+import org.example.carshop.model.User;
+import org.example.carshop.model.enums.RequestStatus;
+import org.example.carshop.model.enums.RequestType;
+import java.time.LocalDate;
+import java.util.Collection;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+/**
+ * Repository class for managing Request entities.
+ */
+@AllArgsConstructor
+public class RequestRepository {
+ private final Map requestsMap;
+
+ /**
+ * Retrieves all requests for a car purchase and a car maintenance.
+ *
+ * @return a collection of all requests.
+ */
+ public Collection getAllRequests() {
+ return requestsMap.values();
+ }
+
+ /**
+ * Adds a new request to the repository.
+ *
+ * @param request the request to add.
+ */
+ public void addRequest(Request request) {
+ requestsMap.put(request.getId(), request);
+ }
+
+ /**
+ * Removes a request from the repository by its ID.
+ *
+ * @param requestId the ID of the request to remove.
+ */
+ public void removeRequestById(int requestId) {
+ requestsMap.remove(requestId);
+ }
+
+ /**
+ * Finds a request by its ID.
+ *
+ * @param requestId the ID of the request to find.
+ * @return the request with the specified ID, or null if not found.
+ */
+ public Request findRequestById(int requestId) {
+ return requestsMap.get(requestId);
+ }
+
+ /**
+ * Filters requests by a specific date and request type.
+ *
+ * @param date the date to filter requests by.
+ * @param requestType the type of request to filter by.
+ * @return a collection of requests that start or end on the specified date and are of the specified type.
+ */
+ public Collection filterRequestsByDateAndType(LocalDate date, RequestType requestType) {
+ return requestsMap.entrySet().stream()
+ .filter(entry -> entry.getValue().getCreationTime().toLocalDate().equals(date)
+ || entry.getValue().getCompletionTime().toLocalDate().equals(date))
+ .filter(entry -> entry.getValue().getRequestType() == requestType)
+ .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue)).values();
+ }
+
+ /**
+ * Filters requests by specific carId.
+ *
+ * @param carId the carId to filter requests by.
+ * @return a collection of requests with the specified carId.
+ */
+ public Collection filterRequestsByCarAndType(int carId, RequestType requestType) {
+ return requestsMap.entrySet().stream()
+ .filter(entry -> entry.getValue().getCarId() == carId)
+ .filter(entry -> entry.getValue().getRequestType() == requestType)
+ .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue)).values();
+ }
+
+ /**
+ * Filters requests by a specific user.
+ *
+ * @param user the user to filter requests by.
+ * @return a collection of requests made by the specified user.
+ */
+ public Collection filterRequestsByUserAndType(User user, RequestType requestType) {
+ return requestsMap.entrySet().stream()
+ .filter(entry -> entry.getValue().getUser() != null && entry.getValue().getUser().equals(user))
+ .filter(entry -> requestType == null || entry.getValue().getRequestType() == requestType)
+ .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue)).values();
+ }
+
+ /**
+ * Filters requests by a specific status.
+ *
+ * @param requestStatus the status to filter requests by.
+ * @return a collection of requests having the specified status.
+ */
+ public Collection filterRequestsByRequestStatusAndType(RequestStatus requestStatus, RequestType requestType) {
+ return requestsMap.entrySet().stream()
+ .filter(entry -> entry.getValue().getRequestStatus().equals(requestStatus))
+ .filter(entry -> entry.getValue().getRequestType() == requestType)
+ .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue)).values();
+ }
+
+ /**
+ * Updates an existing request in the repository.
+ *
+ * @param request the request to add.
+ */
+ public void updateRequest(Request request) {
+ requestsMap.put(request.getId(), request);
+ }
+}
diff --git a/src/main/java/org/example/carshop/repository/UserRepository.java b/src/main/java/org/example/carshop/repository/UserRepository.java
new file mode 100644
index 0000000..ec647a3
--- /dev/null
+++ b/src/main/java/org/example/carshop/repository/UserRepository.java
@@ -0,0 +1,60 @@
+package org.example.carshop.repository;
+
+import lombok.AllArgsConstructor;
+import org.example.carshop.model.User;
+import org.example.carshop.model.enums.UserRole;
+
+import java.util.Collection;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+/**
+ * Repository class for managing users.
+ */
+@AllArgsConstructor
+public class UserRepository {
+ private final Map userMap;
+
+ /**
+ * Registers a new user in the repository.
+ *
+ * @param user The user object to register.
+ */
+ public void registerUser(User user) {
+ userMap.put(user.getUsername(), user);
+ }
+
+ /**
+ * Updates a user in the repository.
+ *
+ * @param user The user object to update.
+ */
+ public void updateUser(User user) {
+ userMap.put(user.getUsername(), user);
+ }
+
+ /**
+ * Finds a user by their username.
+ *
+ * @param username The username of the user to find.
+ * @return The user object with the specified username, or null if not found.
+ */
+ public User findUserByUsername(String username) {
+ return userMap.get(username);
+ }
+
+ /**
+ * Filters users based on given criteria.
+ *
+ * @param name Filter by name.
+ * @param userRoles Filter by roles.
+ * @return filtered collection of users.
+ */
+
+ public Collection filterUsers(String name, Collection userRoles) {
+ return userMap.values().stream()
+ .filter(user -> (name == null || user.getUsername().contains(name))
+ && (userRoles == null || userRoles.contains(user.getRole())))
+ .collect(Collectors.toList());
+ }
+}
diff --git a/src/main/java/org/example/carshop/service/CarShopService.java b/src/main/java/org/example/carshop/service/CarShopService.java
new file mode 100644
index 0000000..cc1e980
--- /dev/null
+++ b/src/main/java/org/example/carshop/service/CarShopService.java
@@ -0,0 +1,74 @@
+package org.example.carshop.service;
+
+import lombok.AllArgsConstructor;
+import org.example.carshop.model.Car;
+import org.example.carshop.repository.CarRepository;
+
+import java.util.Collection;
+
+/**
+ * Service class for managing Car Shop operations.
+ */
+@AllArgsConstructor
+public class CarShopService {
+ private final CarRepository carRepository;
+
+ /**
+ * Retrieves all cars in car shop.
+ *
+ * @return a collection of all cars.
+ */
+ public Collection getAllCars() {
+ return carRepository.getAllCars();
+ }
+
+ /**
+ * Adds a new conference hall.
+ *
+ * @param car the conference hall to add.
+ */
+ public void addCar(Car car) {
+ carRepository.addCar(car);
+ }
+
+ /**
+ * Updates an existing car info.
+ *
+ * @param car the updated car object.
+ */
+ public void updateCar(Car car) {
+ carRepository.updateCar(car);
+ }
+
+ /**
+ * Deletes a car by its ID.
+ *
+ * @param id the ID of the Car to delete.
+ */
+ public void deleteCar(int id) {
+ carRepository.removeCarById(id);
+ }
+
+ /**
+ * Finds a car by its ID.
+ *
+ * @param id the ID of the car to find.
+ * @return the Car with the specified ID, or null if not found.
+ */
+ public Car findCarById(int id) {
+ return carRepository.findCarById(id);
+ }
+
+ /**
+ * Searches for cars based on given parameters.
+ *
+ * @param brand Brand to search by.
+ * @param model Model to search by.
+ * @param prodYear Year of manufacture to search by.
+ * @param isAvailable availability of a car
+ * @return Collection of matching cars.
+ */
+ public Collection searchCars(String brand, String model, String prodYear, Boolean isAvailable) {
+ return carRepository.filterCars(brand, model, prodYear, isAvailable);
+ }
+}
diff --git a/src/main/java/org/example/carshop/service/RequestService.java b/src/main/java/org/example/carshop/service/RequestService.java
new file mode 100644
index 0000000..06214a5
--- /dev/null
+++ b/src/main/java/org/example/carshop/service/RequestService.java
@@ -0,0 +1,104 @@
+package org.example.carshop.service;
+
+import lombok.AllArgsConstructor;
+import org.example.carshop.model.Car;
+import org.example.carshop.model.enums.RequestStatus;
+import org.example.carshop.model.enums.RequestType;
+import org.example.carshop.model.Request;
+import org.example.carshop.model.User;
+import org.example.carshop.repository.RequestRepository;
+import java.time.LocalDate;
+import java.util.Collection;
+
+/**
+ * Service class for managing requests.
+ */
+@AllArgsConstructor
+public class RequestService {
+ private final RequestRepository requestRepository;
+
+ /**
+ * Adds a new request to the repository.
+ *
+ * @param request The requests to add.
+ */
+ public void addRequest(Request request) {
+ requestRepository.addRequest(request);
+ }
+
+ /**
+ * Deletes a request from the repository based on its ID.
+ *
+ * @param requestId The ID of the request to delete.
+ */
+ public void deleteRequest(int requestId) {
+ requestRepository.removeRequestById(requestId);
+ }
+
+ /**
+ * Retrieves all requests from the repository.
+ *
+ * @return A collection of all requests.
+ */
+ public Collection getAllRequests() {
+ return requestRepository.getAllRequests();
+ }
+
+ /**
+ * Filters requests based on a specified date.
+ *
+ * @param date The date to filter requests by.
+ * @return A collection of requests that match the specified date.
+ */
+ public Collection filterRequestsByDateAndType(LocalDate date, RequestType requestType) {
+ return requestRepository.filterRequestsByDateAndType(date, requestType);
+ }
+
+ /**
+ * Filters requests by specific carId.
+ *
+ * @param carId the carId to filter requests by.
+ * @return a collection of requests made for specific car.
+ */
+ public Collection filterRequestsByCarAndType(int carId, RequestType requestType) {
+ return requestRepository.filterRequestsByCarAndType(carId, requestType);
+ }
+
+ /**
+ * Filters requests based on a specified user.
+ *
+ * @param user The user to filter requests by.
+ * @return A collection of requests that belong to the specified user.
+ */
+ public Collection filterRequestsByUserAndType(User user, RequestType requestType) {
+ return requestRepository.filterRequestsByUserAndType(user, requestType);
+ }
+
+ /**
+ * Filters requests by a specific status.
+ *
+ * @param requestStatus the status to filter requests by.
+ * @return a collection of requests having the specified status.
+ */
+ public Collection filterRequestsByRequestStatusAndType(RequestStatus requestStatus, RequestType requestType) {
+ return requestRepository.filterRequestsByRequestStatusAndType(requestStatus, requestType);
+ }
+ /**
+ * Finds a request by its ID.
+ *
+ * @param id The ID of the request to find.
+ * @return The request with the specified ID, or null if not found.
+ */
+ public Request findRequestById(int id) {
+ return requestRepository.findRequestById(id);
+ }
+
+ /**
+ * Updates an existing car in the repository.
+ *
+ * @param request the car object with updated information.
+ */
+ public void updateRequest(Request request) {
+ requestRepository.updateRequest(request);
+ }
+}
diff --git a/src/main/java/org/example/carshop/service/UserService.java b/src/main/java/org/example/carshop/service/UserService.java
new file mode 100644
index 0000000..cf6ca7f
--- /dev/null
+++ b/src/main/java/org/example/carshop/service/UserService.java
@@ -0,0 +1,66 @@
+package org.example.carshop.service;
+
+import lombok.AllArgsConstructor;
+
+import org.example.carshop.model.User;
+import org.example.carshop.model.enums.UserRole;
+import org.example.carshop.repository.UserRepository;
+
+import java.util.Collection;
+
+/**
+ * Service class for managing User operations.
+ */
+@AllArgsConstructor
+public class UserService {
+ private final UserRepository userRepository;
+
+ /**
+ * Registers a new user.
+ *
+ * @param user the user to register.
+ */
+ public void register(User user) {
+ userRepository.registerUser(user);
+ }
+
+ /**
+ * Logs in a user by checking if the credentials match.
+ *
+ * @param userParam the user attempting to log in.
+ * @return true if the credentials match, otherwise false.
+ */
+ public boolean login(User userParam) {
+ return userRepository.findUserByUsername(userParam.getUsername()).getPassword()
+ .equals(userParam.getPassword());
+ }
+
+ /**
+ * Finds a user by their username.
+ *
+ * @param username the username to search for.
+ * @return the user with the specified username, or null if not found.
+ */
+ public User findUserByName(String username) {
+ return userRepository.findUserByUsername(username);
+ }
+
+ /**
+ * Filters users based on given criteria.
+ *
+ * @param name Filter by name.
+ * @param userRoles Filter by role
+ * @return filtered collection of users.
+ */
+ public Collection searchUsers(String name, Collection userRoles) {
+ return userRepository.filterUsers(name, userRoles);
+ }
+ /**
+ * Updates an existing user in the repository.
+ *
+ * @param user the request to add.
+ */
+ public void updateUser(User user) {
+ userRepository.updateUser(user);
+ }
+}
diff --git a/src/test/java/CarShopServiceTest.java b/src/test/java/CarShopServiceTest.java
new file mode 100644
index 0000000..c3cb865
--- /dev/null
+++ b/src/test/java/CarShopServiceTest.java
@@ -0,0 +1,101 @@
+import org.example.carshop.model.Car;
+import org.example.carshop.repository.CarRepository;
+import org.example.carshop.service.CarShopService;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.DisplayName;
+import org.junit.jupiter.api.Test;
+
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Map;
+
+import static org.assertj.core.api.Assertions.assertThat;
+
+@DisplayName("Tests for CarShopService class")
+public class CarShopServiceTest {
+
+ private CarShopService carShopService;
+ private Map carMap;
+
+ @BeforeEach
+ public void setUp() {
+ carMap = new HashMap<>();
+ CarRepository carRepository = new CarRepository(carMap);
+ carShopService = new CarShopService(carRepository);
+ }
+
+ @Test
+ @DisplayName("Test adding a car")
+ public void testAddCar() {
+ // Arrange
+ Car car = new Car(1, "Model1", "Brand1", "2020","Great", true);
+
+ // Act
+ carShopService.addCar(car);
+
+ // Assert
+ assertThat(carMap).hasSize(1);
+ assertThat(carMap.get(1)).isEqualTo(car);
+ }
+
+ @Test
+ @DisplayName("Test retrieving available cars")
+ public void testGetAvailableCars() {
+ // Arrange
+ Car car1 = new Car(1, "Model1", "Brand1", "2020","Great", true);
+ Car car2 = new Car(2, "Model2", "Brand2", "2020","Great", true);
+ carShopService.addCar(car1);
+ carShopService.addCar(car2);
+
+ // Act
+ Collection cars = carShopService.getAllCars();
+
+ // Assert
+ assertThat(cars).hasSize(2);
+ }
+
+
+ @Test
+ @DisplayName("Test updating a car")
+ public void testUpdateCar() {
+ // Arrange
+ Car car = new Car(1, "Model1", "Brand1", "2020","Great", true);
+ carMap.put(car.getId(), car);
+
+ // Act
+ Car updatedCar = new Car(1, "Model2", "Brand2", "2022","So-So", false);
+ carShopService.updateCar(updatedCar);
+
+ // Assert
+ assertThat(carMap.get(car.getId())).isEqualTo(updatedCar);
+ assertThat(carMap.get(car.getId()).isAvailable()).isFalse();
+ }
+
+ @Test
+ @DisplayName("Test deleting a car")
+ public void testDeleteCar() {
+ // Arrange
+ Car car = new Car(1, "Model1", "Brand1", "2020","Great", true);
+ carMap.put(car.getId(), car);
+
+ // Act
+ carShopService.deleteCar(1);
+
+ // Assert
+ assertThat(carMap).isEmpty();
+ }
+
+ @Test
+ @DisplayName("Test finding a ConferenceHall by ID")
+ public void testFindCarById() {
+ // Arrange
+ Car car = new Car(1, "Model1", "Brand1", "2020","Great", true);
+ carMap.put(car.getId(), car);
+
+ // Act
+ Car foundCar = carShopService.findCarById(1);
+
+ // Assert
+ assertThat(foundCar).isEqualTo(car);
+ }
+}
diff --git a/src/test/java/CarTest.java b/src/test/java/CarTest.java
new file mode 100644
index 0000000..996bde5
--- /dev/null
+++ b/src/test/java/CarTest.java
@@ -0,0 +1,52 @@
+import org.example.carshop.model.Car;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.DisplayName;
+import org.junit.jupiter.api.Test;
+import static org.assertj.core.api.Assertions.assertThat;
+
+@DisplayName("Tests for Car class")
+public class CarTest {
+
+ private Car car;
+
+ @BeforeEach
+ public void setUp() {
+ car = new Car(1, "Model1", "Brand1", "2020","Great", true);;
+ }
+
+ @Test
+ @DisplayName("Test constructor and getters")
+ public void testConstructorAndGetters() {
+ assertThat(car.getId()).isEqualTo(1);
+ assertThat(car.getModelName()).isEqualTo("Model1");
+ assertThat(car.getBrandName()).isEqualTo("Brand1");
+ assertThat(car.getProdYear()).isEqualTo("2020");
+ assertThat(car.getStateDesc()).isEqualTo("Great");
+ assertThat(car.isAvailable()).isTrue();
+ }
+
+ @Test
+ @DisplayName("Test setters")
+ public void testSetters() {
+ car.setId(2);
+ car.setModelName("Model2");
+ car.setBrandName("Brand2");
+ car.setProdYear("2022");
+ car.setStateDesc("Great2");
+ car.setAvailable(false);
+
+ assertThat(car.getId()).isEqualTo(2);
+ assertThat(car.getModelName()).isEqualTo("Model2");
+ assertThat(car.getBrandName()).isEqualTo("Brand2");
+ assertThat(car.getProdYear()).isEqualTo("2022");
+ assertThat(car.getStateDesc()).isEqualTo("Great2");
+ assertThat(car.isAvailable()).isFalse();
+ }
+
+ @Test
+ @DisplayName("Test toString method")
+ public void testToString() {
+ String expectedString = "Car(id=1, modelName=Model1, brandName=Brand1, prodYear=2020, stateDesc=Great, isAvailable=true)";
+ assertThat(car.toString()).isEqualTo(expectedString);
+ }
+}
diff --git a/src/test/java/RequestServiceTest.java b/src/test/java/RequestServiceTest.java
new file mode 100644
index 0000000..3732a88
--- /dev/null
+++ b/src/test/java/RequestServiceTest.java
@@ -0,0 +1,168 @@
+import org.example.carshop.model.enums.RequestStatus;
+import org.example.carshop.model.enums.RequestType;
+import org.example.carshop.model.Request;
+import org.example.carshop.model.User;
+import org.example.carshop.repository.RequestRepository;
+import org.example.carshop.service.RequestService;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.DisplayName;
+import org.junit.jupiter.api.Test;
+
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Map;
+
+import static org.assertj.core.api.Assertions.assertThat;
+
+@DisplayName("RequestService Tests")
+public class RequestServiceTest {
+
+ private RequestService requestService;
+ private RequestRepository requestRepository;
+ private Map requestMap;
+
+ @BeforeEach
+ public void setUp() {
+ requestMap = new HashMap<>();
+ requestRepository = new RequestRepository(requestMap);
+ requestService = new RequestService(requestRepository);
+ }
+
+ @Test
+ @DisplayName("Test creating a request")
+ public void testCreateRequest() {
+ // Arrange
+ LocalDateTime startTime = LocalDateTime.of(2024, 1, 1, 1, 0);
+ LocalDateTime endTime = LocalDateTime.of(2024, 1, 1, 2, 0);
+ int carId = 1;
+ RequestType requestType = RequestType.ORDER;
+ RequestStatus requestStatus = RequestStatus.NEW;
+
+ // Act
+ Request request = new Request(null, carId, startTime, endTime, requestType, requestStatus);
+ requestService.addRequest(request);
+
+ // Assert
+ assertThat(requestMap).hasSize(1);
+ Request createdRequest = requestMap.get(request.getId());
+ assertThat(createdRequest.getId()).isEqualTo(request.getId());
+ assertThat(createdRequest.getCarId()).isEqualTo(carId);
+ assertThat(createdRequest.getCreationTime()).isEqualTo(startTime);
+ assertThat(createdRequest.getCompletionTime()).isEqualTo(endTime);
+ assertThat(createdRequest.getRequestType()).isEqualTo(requestType);
+ assertThat(createdRequest.getRequestStatus()).isEqualTo(requestStatus);
+ }
+
+ @Test
+ @DisplayName("Test deleting a request")
+ public void testDeleteRequest() {
+ // Arrange
+ Request request1 = new Request(null, 1, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ Request request2 = new Request(null, 2, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ requestMap.put(request1.getId(), request1);
+ requestMap.put(request2.getId(), request2);
+
+ // Act
+ requestService.deleteRequest(request1.getId());
+
+ // Assert
+ assertThat(requestMap).hasSize(1);
+ assertThat(requestMap.get(request2.getId()).getId()).isEqualTo(request2.getId());
+ }
+
+ @Test
+ @DisplayName("Test viewing all Requests")
+ public void testViewAllRequests() {
+ // Arrange
+ Request request1 = new Request(null, 1, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ Request request2 = new Request(null, 2, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ requestMap.put(request1.getId(), request1);
+ requestMap.put(request2.getId(), request2);
+
+ // Act
+ Collection allReqs = requestService.getAllRequests();
+
+ // Assert
+ assertThat(allReqs).hasSize(2);
+ }
+
+ @Test
+ @DisplayName("Test filtering Requests by date")
+ public void testFilterRequestsByDate() {
+ // Arrange
+ LocalDateTime newStartTime1 = LocalDateTime.of(2024, 6, 24, 9, 0);
+ LocalDateTime newEndTime2 = LocalDateTime.of(2024, 6, 25, 11, 0);
+ Request request1 = new Request(null, 1, newStartTime1, newEndTime2, RequestType.ORDER, RequestStatus.NEW);
+ Request request2 = new Request(null, 2, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ requestMap.put(request1.getId(), request1);
+ requestMap.put(request2.getId(), request2);
+
+ // Act
+ Collection filteredMap = requestService.filterRequestsByDateAndType(LocalDate.from(newStartTime1), request1.getRequestType());
+ Request firstRequest = filteredMap.stream().findFirst().orElse(null);
+
+ // Assert
+ assertThat(filteredMap).hasSize(1);
+ assertThat(firstRequest.getId()).isEqualTo(request1.getId());
+ }
+
+ @Test
+ @DisplayName("Test filtering Requests by user")
+ public void testFilterRequestsByUser() {
+ // Arrange
+ User user1 = new User("us1", "password");
+ User user2 = new User("us2", "password");
+ Request request1 = new Request(null, 1, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ Request request2 = new Request(null, 2, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ request1.setUser(user1);
+ request2.setUser(user2);
+ requestMap.put(request1.getId(), request1);
+ requestMap.put(request2.getId(), request2);
+
+ // Act
+ Collection filteredMap = requestService.filterRequestsByUserAndType(user1, request1.getRequestType());
+ Request firstRequest = filteredMap.stream().findFirst().orElse(null);
+
+ // Assert
+ assertThat(filteredMap).hasSize(1);
+ assertThat(firstRequest.getId()).isEqualTo(request1.getId());
+ }
+
+ @Test
+ @DisplayName("Test filtering Requests by car")
+ public void testFilterRequestsByCar() {
+ // Arrange
+ RequestType requestType = RequestType.ORDER;
+ Request request1 = new Request(null, 1, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ Request request2 = new Request(null, 2, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ requestMap.put(request1.getId(), request1);
+ requestMap.put(request2.getId(), request2);
+
+ // Act
+ Collection filteredMap = requestService.filterRequestsByCarAndType(1,requestType);
+ Request firstRequest = filteredMap.stream().findFirst().orElse(null);
+
+ // Assert
+ assertThat(filteredMap).hasSize(1);
+ assertThat(firstRequest.getId()).isEqualTo(request1.getId());
+ }
+
+ @Test
+ @DisplayName("Test finding a Requests by ID")
+ public void testFindRequestById() {
+ // Arrange
+ Request request1 = new Request(null, 1, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ Request request2 = new Request(null, 2, LocalDateTime.now(), LocalDateTime.now().plusHours(1), RequestType.ORDER, RequestStatus.NEW);
+ requestMap.put(request1.getId(), request1);
+ requestMap.put(request2.getId(), request2);
+
+ // Act
+ Request foundRequest = requestService.findRequestById(request1.getId());
+
+ // Assert
+ assertThat(foundRequest).isNotNull();
+ assertThat(foundRequest.getId()).isEqualTo(request1.getId());
+ }
+}
diff --git a/src/test/java/RequestTest.java b/src/test/java/RequestTest.java
new file mode 100644
index 0000000..d0eebfc
--- /dev/null
+++ b/src/test/java/RequestTest.java
@@ -0,0 +1,68 @@
+import org.example.carshop.model.enums.RequestStatus;
+import org.example.carshop.model.enums.RequestType;
+import org.example.carshop.model.Request;
+import org.example.carshop.model.User;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.DisplayName;
+import org.junit.jupiter.api.Test;
+import org.mockito.MockitoAnnotations;
+
+import java.time.LocalDateTime;
+
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.mockito.Mockito.*;
+
+@DisplayName("Tests for Request clas")
+public class RequestTest {
+
+ private Request request;
+ private User mockUser;
+
+ @BeforeEach
+ public void setUp() {
+ MockitoAnnotations.openMocks(this);
+ mockUser = mock(User.class);
+ request = new Request(mockUser, 101,
+ LocalDateTime.of(2024, 6, 24, 10, 0),
+ LocalDateTime.of(2024, 6, 24, 12, 0),
+ RequestType.ORDER,
+ RequestStatus.NEW
+ );
+ }
+
+ @Test
+ @DisplayName("Test constructor and getters")
+ public void testConstructorAndGetters() {
+ assertThat(request.getId()).isEqualTo(14);
+ assertThat(request.getCarId()).isEqualTo(101);
+ assertThat(request.getCreationTime()).isEqualTo(LocalDateTime.of(2024, 6, 24, 10, 0));
+ assertThat(request.getCompletionTime()).isEqualTo(LocalDateTime.of(2024, 6, 24, 12, 0));
+ assertThat(request.getRequestType()).isEqualTo(RequestType.ORDER);
+ }
+
+ @Test
+ @DisplayName("Test setters")
+ public void testSetters() {
+ request.setId(2);
+ request.setCarId(102);
+ LocalDateTime newStartTime = LocalDateTime.of(2024, 6, 25, 9, 0);
+ LocalDateTime newEndTime = LocalDateTime.of(2024, 6, 25, 11, 0);
+ request.setCreationTime(newStartTime);
+ request.setCompletionTime(newEndTime);
+ request.setRequestType(RequestType.MAINTENANCE);
+
+ assertThat(request.getId()).isEqualTo(2);
+ assertThat(request.getCarId()).isEqualTo(102);
+ assertThat(request.getCreationTime()).isEqualTo(newStartTime);
+ assertThat(request.getCompletionTime()).isEqualTo(newEndTime);
+ assertThat(request.getRequestType()).isEqualTo(RequestType.MAINTENANCE);
+ }
+
+ @Test
+ @DisplayName("Test setUser method")
+ public void testSetUser() {
+ request.setUser(mockUser);
+ assertThat(request.getUser()).isEqualTo(mockUser);
+ }
+
+}
diff --git a/src/test/java/UserServiceTest.java b/src/test/java/UserServiceTest.java
new file mode 100644
index 0000000..e8ad60f
--- /dev/null
+++ b/src/test/java/UserServiceTest.java
@@ -0,0 +1,88 @@
+import org.example.carshop.model.User;
+import org.example.carshop.model.enums.UserRole;
+import org.example.carshop.repository.UserRepository;
+import org.example.carshop.service.UserService;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.DisplayName;
+import org.junit.jupiter.api.Test;
+import org.mockito.InjectMocks;
+import org.mockito.Mock;
+import org.mockito.MockitoAnnotations;
+
+import static org.assertj.core.api.Assertions.assertThat;
+import static org.mockito.ArgumentMatchers.any;
+import static org.mockito.Mockito.*;
+
+@DisplayName("UserService Tests")
+class UserServiceTest {
+
+ @Mock
+ private UserRepository userRepository;
+
+ @InjectMocks
+ private UserService userService;
+
+ @BeforeEach
+ void setUp() {
+ MockitoAnnotations.openMocks(this);
+ }
+
+ @Test
+ @DisplayName("Register User Test")
+ void register() {
+ // Arrange
+ User user = new User("user1", "password1", "fullname",UserRole.CLIENT);
+
+ // Act
+ userService.register(user);
+
+ // Assert
+ verify(userRepository, times(1)).registerUser(any(User.class));
+ }
+
+ @Test
+ @DisplayName("Login Successful Test")
+ void loginSuccessful() {
+ // Arrange
+ User user = new User("user1", "password1", "fullname",UserRole.CLIENT);
+ when(userRepository.findUserByUsername("user1")).thenReturn(user);
+
+ // Act
+ boolean result = userService.login(user);
+
+ // Assert
+ assertThat(result).isTrue();
+ verify(userRepository, times(1)).findUserByUsername("user1");
+ }
+
+ @Test
+ @DisplayName("Login Failed Test")
+ void loginFailed() {
+ // Arrange
+ User user = new User("user1", "password1", "fullname",UserRole.CLIENT);
+ User storedUser = new User("user1", "password2", "fullname",UserRole.CLIENT);
+ when(userRepository.findUserByUsername("user1")).thenReturn(storedUser);
+
+ // Act
+ boolean result = userService.login(user);
+
+ // Assert
+ assertThat(result).isFalse();
+ verify(userRepository, times(1)).findUserByUsername("user1");
+ }
+
+ @Test
+ @DisplayName("Find User By Name Test")
+ void findUserByName() {
+ // Arrange
+ User user = new User("user1", "password1", "fullname",UserRole.CLIENT);
+ when(userRepository.findUserByUsername("user1")).thenReturn(user);
+
+ // Act
+ User foundUser = userService.findUserByName("user1");
+
+ // Assert
+ assertThat(foundUser).isEqualTo(user);
+ verify(userRepository, times(1)).findUserByUsername("user1");
+ }
+}
diff --git a/src/test/java/UserTest.java b/src/test/java/UserTest.java
new file mode 100644
index 0000000..aaf2e0f
--- /dev/null
+++ b/src/test/java/UserTest.java
@@ -0,0 +1,46 @@
+import org.example.carshop.model.User;
+import org.example.carshop.model.enums.UserRole;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.DisplayName;
+import org.junit.jupiter.api.Test;
+import org.mockito.MockitoAnnotations;
+import static org.assertj.core.api.Assertions.assertThat;
+
+@DisplayName("User Class Tests")
+public class UserTest {
+
+ private User user;
+
+ @BeforeEach
+ public void setUp() {
+ MockitoAnnotations.openMocks(this);
+ user = new User("testUser", "password123", "fullname",UserRole.ADMIN);
+ }
+
+ @Test
+ @DisplayName("Test Constructor and Getters")
+ public void testConstructorAndGetters() {
+ assertThat(user.getUsername()).isEqualTo("testUser");
+ assertThat(user.getPassword()).isEqualTo("password123");
+ assertThat(user.getRole()).isEqualTo(UserRole.ADMIN);
+ }
+
+ @Test
+ @DisplayName("Test Setters")
+ public void testSetters() {
+ user.setUsername("newUsername");
+ user.setPassword("newPassword456");
+ user.setRole(UserRole.ADMIN);
+
+ assertThat(user.getUsername()).isEqualTo("newUsername");
+ assertThat(user.getPassword()).isEqualTo("newPassword456");
+ assertThat(user.getRole()).isEqualTo(UserRole.ADMIN);
+ }
+
+ @Test
+ @DisplayName("Test toString() Method")
+ public void testToString() {
+ String expectedString = "User{username='testUser', role=ADMIN}";
+ assertThat(user.toString()).isEqualTo(expectedString);
+ }
+}