182 lines
6.8 KiB
Java
182 lines
6.8 KiB
Java
package me.zinch.console;
|
||
|
||
import me.zinch.commands.CommandManager;
|
||
import me.zinch.exceptions.ColorFormatException;
|
||
import me.zinch.exceptions.CommandActionException;
|
||
import me.zinch.exceptions.UnitOfMeasureFormatException;
|
||
import me.zinch.exceptions.ValidationException;
|
||
import me.zinch.files.DbController;
|
||
import me.zinch.models.Color;
|
||
import me.zinch.models.Coordinates;
|
||
import me.zinch.models.Location;
|
||
import me.zinch.models.Person;
|
||
import me.zinch.models.ProductDTO;
|
||
import me.zinch.models.UnitOfMeasure;
|
||
import me.zinch.validator.ValidateResult;
|
||
import me.zinch.validator.Validators;
|
||
import me.zinch.wrapper.ProductCollection;
|
||
|
||
import java.io.IOException;
|
||
import java.util.ArrayList;
|
||
import java.util.List;
|
||
import java.util.NoSuchElementException;
|
||
import java.util.Scanner;
|
||
|
||
/**
|
||
Console class provides methods for interacting with the console, reading user input, and managing application flow.
|
||
This class includes methods for appending input history, stopping the application, reading product DTO from the console, and running the application loop.
|
||
*/
|
||
public class Console {
|
||
private static final Scanner scanner = new Scanner(System.in);
|
||
private static boolean isRunning = true;
|
||
private static final List<String> history = new ArrayList<>();
|
||
|
||
public static void appendHistory(String input) {
|
||
history.add(input);
|
||
}
|
||
|
||
public static void stopApp() {
|
||
isRunning = false;
|
||
scanner.close();
|
||
}
|
||
|
||
public static String getLastCommand() {
|
||
return history.get(history.size() - 1);
|
||
}
|
||
|
||
|
||
private static String readString() {
|
||
var input = scanner.nextLine().trim();
|
||
return input.isEmpty() ? null : input;
|
||
}
|
||
|
||
private static Long readLong() {
|
||
var input = scanner.nextLine().trim();
|
||
if (input.isEmpty()) return null;
|
||
try {
|
||
return Long.parseLong(input);
|
||
} catch (NumberFormatException e) {
|
||
throw new NumberFormatException(String.format("Не могу распознать %s как число", input));
|
||
}
|
||
}
|
||
|
||
private static Color readColor() throws ColorFormatException {
|
||
System.out.format("Цвет волос(%s): ", Color.getColorsString());
|
||
var input = readString();
|
||
if (input == null || input.isEmpty()) return null;
|
||
try {
|
||
return Color.create(Integer.parseInt(input));
|
||
} catch (NumberFormatException | ArrayIndexOutOfBoundsException e) {
|
||
try {
|
||
return Color.create(input);
|
||
} catch (IllegalArgumentException ex) {
|
||
throw new ColorFormatException(ex.getMessage());
|
||
}
|
||
}
|
||
}
|
||
|
||
private static UnitOfMeasure readUnitOfMeasure() throws UnitOfMeasureFormatException {
|
||
System.out.format("Единица измерения(%s): ", UnitOfMeasure.getUnitOfMeasuerString());
|
||
var input = readString();
|
||
try {
|
||
return UnitOfMeasure.create(Integer.parseInt(input));
|
||
} catch (NumberFormatException | ArrayIndexOutOfBoundsException e) {
|
||
try {
|
||
return UnitOfMeasure.create(input);
|
||
} catch (IllegalArgumentException ex) {
|
||
throw new ColorFormatException(ex.getMessage());
|
||
}
|
||
}
|
||
}
|
||
|
||
private static Location readLocation() throws NumberFormatException {
|
||
System.out.print("Создать поле Location? (Y/n): ");
|
||
var input = readString();
|
||
if (input != null && input.equalsIgnoreCase("n")) return null;
|
||
System.out.print("Координата x локации: ");
|
||
var locationX = Float.parseFloat(readString());
|
||
System.out.print("Координата y локации: ");
|
||
var locationY = Integer.parseInt(readString());
|
||
System.out.print("Название: ");
|
||
var locationName = readString();
|
||
return new Location(locationX, locationY, locationName);
|
||
}
|
||
|
||
private static void readField(String fieldName, Runnable function) {
|
||
while (true) {
|
||
if (fieldName != null) System.out.format("%s: ", fieldName);
|
||
try {
|
||
function.run();
|
||
return;
|
||
} catch (NullPointerException e) {
|
||
System.out.println("Произошла ошибка при заполнении поля\nПоле не может быть null");
|
||
} catch (Exception e) {
|
||
System.out.format("Произошла ошибка при заполнении поля%n%s%n", e.getMessage());
|
||
}
|
||
}
|
||
}
|
||
|
||
private static void readField(Runnable function) {
|
||
readField(null, function);
|
||
}
|
||
|
||
public static ProductDTO readProductDTO() {
|
||
var productDTO = new ProductDTO();
|
||
var coordinates = new Coordinates();
|
||
var owner = new Person();
|
||
System.out.println("Заполните следующие поля: ");
|
||
|
||
readField("Название", () -> productDTO.setName(readString()));
|
||
readField("Координата x", () -> coordinates.setX(readLong()));
|
||
readField("Координата y", () -> coordinates.setY(readLong()));
|
||
readField("Цена", () -> productDTO.setPrice(readLong()));
|
||
readField("Номер части", () -> productDTO.setPartNumber(readString()));
|
||
readField("Себестоимость", () -> productDTO.setManufactureCost(readLong()));
|
||
readField(() -> productDTO.setUnitOfMeasure(readUnitOfMeasure()));
|
||
readField("Имя владельца", () -> owner.setName(readString()));
|
||
readField("Данные паспорта", () -> owner.setPassportID(readString()));
|
||
readField(() -> owner.setHairColor(readColor()));
|
||
readField(() -> owner.setLocation(readLocation()));
|
||
|
||
productDTO.setCoordinates(coordinates);
|
||
productDTO.setOwner(owner);
|
||
return productDTO;
|
||
}
|
||
|
||
public static void run() throws IOException, ValidationException {
|
||
var productList = DbController.loadDb();
|
||
var validationResult = Validators.validateProductList(productList);
|
||
if (!validationResult.stream().allMatch(ValidateResult::isValid)) {
|
||
throw new ValidationException(String.join("\n", validationResult
|
||
.stream()
|
||
.map(ValidateResult::getMessage)
|
||
.toList()));
|
||
}
|
||
|
||
var productCollection = new ProductCollection(productList);
|
||
System.out.println("Добро пожаловать! Для просмотра команд введите help");
|
||
|
||
while(isRunning) {
|
||
System.out.print(":");
|
||
try {
|
||
var input = scanner.nextLine().trim();
|
||
var command = CommandManager.getCommandByInput(input);
|
||
if (command.isPresent()) {
|
||
appendHistory(input);
|
||
try {
|
||
System.out.println(command.get().action(productCollection));
|
||
} catch (CommandActionException e) {
|
||
System.out.println(e.getMessage());
|
||
}
|
||
} else {
|
||
System.out.println("Такой команды не существует. Напишите help, чтобы посмотреть список доступных команд.");
|
||
}
|
||
} catch (NoSuchElementException e) {
|
||
stopApp();
|
||
}
|
||
System.out.println();
|
||
}
|
||
System.out.println("Всего хорошего!");
|
||
}
|
||
}
|