From 2f49648047e60bd4a7e14b58a8ebb2a2a2046201 Mon Sep 17 00:00:00 2001 From: Anurag Agarwal Date: Sun, 10 Nov 2019 01:05:15 +0530 Subject: [PATCH] Resolves checkstyle errors for collection-pipeline, command, commander (#1061) * Reduces checkstyle errors in collection-pipeline * Reduces checkstyle errors in command * Reduces checkstyle errors in commander --- .../com/iluwatar/collectionpipeline/App.java | 42 +- .../com/iluwatar/collectionpipeline/Car.java | 9 +- .../collectionpipeline/CarFactory.java | 1 + .../iluwatar/collectionpipeline/Category.java | 2 +- .../FunctionalProgramming.java | 43 +-- .../ImperativeProgramming.java | 53 ++- .../iluwatar/collectionpipeline/Person.java | 1 + .../iluwatar/collectionpipeline/AppTest.java | 29 +- .../main/java/com/iluwatar/command/App.java | 27 +- .../java/com/iluwatar/command/Command.java | 2 - .../java/com/iluwatar/command/Goblin.java | 4 +- .../iluwatar/command/InvisibilitySpell.java | 4 +- .../com/iluwatar/command/ShrinkSpell.java | 4 +- .../main/java/com/iluwatar/command/Size.java | 2 - .../java/com/iluwatar/command/Target.java | 4 +- .../java/com/iluwatar/command/Visibility.java | 2 - .../java/com/iluwatar/command/Wizard.java | 15 +- .../commander/AppEmployeeDbFailCases.java | 50 +-- .../commander/AppMessagingFailCases.java | 95 +++-- .../commander/AppPaymentFailCases.java | 43 ++- .../iluwatar/commander/AppQueueFailCases.java | 99 +++-- .../commander/AppShippingFailCases.java | 55 +-- .../com/iluwatar/commander/Commander.java | 361 ++++++++++-------- .../java/com/iluwatar/commander/Database.java | 8 +- .../java/com/iluwatar/commander/Order.java | 12 +- .../java/com/iluwatar/commander/Retry.java | 37 +- .../java/com/iluwatar/commander/Service.java | 28 +- .../employeehandle/EmployeeDatabase.java | 8 +- .../employeehandle/EmployeeHandle.java | 12 +- .../DatabaseUnavailableException.java | 4 +- .../PaymentDetailsErrorException.java | 4 +- .../ShippingNotPossibleException.java | 4 +- .../messagingservice/MessagingDatabase.java | 6 +- .../messagingservice/MessagingService.java | 35 +- .../paymentservice/PaymentDatabase.java | 7 +- .../paymentservice/PaymentService.java | 16 +- .../com/iluwatar/commander/queue/Queue.java | 14 +- .../commander/queue/QueueDatabase.java | 19 +- .../iluwatar/commander/queue/QueueTask.java | 34 +- .../shippingservice/ShippingDatabase.java | 8 +- .../shippingservice/ShippingService.java | 17 +- 41 files changed, 646 insertions(+), 574 deletions(-) diff --git a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/App.java b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/App.java index de19a3b15..e0cc904d6 100644 --- a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/App.java +++ b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/App.java @@ -23,21 +23,18 @@ package com.iluwatar.collectionpipeline; +import java.util.List; +import java.util.Map; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import java.util.List; -import java.util.Map; - /** - * In imperative-style programming, it is common to use for and while loops for - * most kinds of data processing. Function composition is a simple technique - * that lets you sequence modular functions to create more complex operations. - * When you run data through the sequence, you have a collection pipeline. - * Together, the Function Composition and Collection Pipeline patterns enable - * you to create sophisticated programs where data flow from upstream to - * downstream and is passed through a series of transformations. - * + * In imperative-style programming, it is common to use for and while loops for most kinds of data + * processing. Function composition is a simple technique that lets you sequence modular functions + * to create more complex operations. When you run data through the sequence, you have a collection + * pipeline. Together, the Function Composition and Collection Pipeline patterns enable you to + * create sophisticated programs where data flow from upstream to downstream and is passed through a + * series of transformations. */ public class App { @@ -45,32 +42,35 @@ public class App { /** * Program entry point. - * - * @param args - * command line args + * + * @param args command line args */ public static void main(String[] args) { List cars = CarFactory.createCars(); - + List modelsImperative = ImperativeProgramming.getModelsAfter2000(cars); LOGGER.info(modelsImperative.toString()); List modelsFunctional = FunctionalProgramming.getModelsAfter2000(cars); LOGGER.info(modelsFunctional.toString()); - - Map> groupingByCategoryImperative = ImperativeProgramming.getGroupingOfCarsByCategory(cars); + + Map> groupingByCategoryImperative = + ImperativeProgramming.getGroupingOfCarsByCategory(cars); LOGGER.info(groupingByCategoryImperative.toString()); - Map> groupingByCategoryFunctional = FunctionalProgramming.getGroupingOfCarsByCategory(cars); + Map> groupingByCategoryFunctional = + FunctionalProgramming.getGroupingOfCarsByCategory(cars); LOGGER.info(groupingByCategoryFunctional.toString()); - + Person john = new Person(cars); - List sedansOwnedImperative = ImperativeProgramming.getSedanCarsOwnedSortedByDate(List.of(john)); + List sedansOwnedImperative = + ImperativeProgramming.getSedanCarsOwnedSortedByDate(List.of(john)); LOGGER.info(sedansOwnedImperative.toString()); - List sedansOwnedFunctional = FunctionalProgramming.getSedanCarsOwnedSortedByDate(List.of(john)); + List sedansOwnedFunctional = + FunctionalProgramming.getSedanCarsOwnedSortedByDate(List.of(john)); LOGGER.info(sedansOwnedFunctional.toString()); } } diff --git a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Car.java b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Car.java index 314728797..2828cffd4 100644 --- a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Car.java +++ b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Car.java @@ -34,10 +34,11 @@ public class Car { /** * Constructor to create an instance of car. - * @param make the make of the car - * @param model the model of the car + * + * @param make the make of the car + * @param model the model of the car * @param yearOfMake the year of built of the car - * @param category the {@link Category} of the car + * @param category the {@link Category} of the car */ public Car(String make, String model, int yearOfMake, Category category) { this.make = make; @@ -103,7 +104,7 @@ public class Car { public int getYear() { return year; } - + public Category getCategory() { return category; } diff --git a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/CarFactory.java b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/CarFactory.java index aee1e2193..ea29ceda6 100644 --- a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/CarFactory.java +++ b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/CarFactory.java @@ -34,6 +34,7 @@ public class CarFactory { /** * Factory method to create a {@link List} of {@link Car} instances. + * * @return {@link List} of {@link Car} */ public static List createCars() { diff --git a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Category.java b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Category.java index 170d4df33..2214ebd4c 100644 --- a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Category.java +++ b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Category.java @@ -24,7 +24,7 @@ package com.iluwatar.collectionpipeline; /** - * Enum for the category of car + * Enum for the category of car. */ public enum Category { JEEP, SEDAN, CONVERTIBLE diff --git a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/FunctionalProgramming.java b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/FunctionalProgramming.java index 2a72aa008..bb216d2bc 100644 --- a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/FunctionalProgramming.java +++ b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/FunctionalProgramming.java @@ -30,20 +30,17 @@ import java.util.stream.Collectors; /** * Iterating and sorting with a collection pipeline - * + * *

In functional programming, it's common to sequence complex operations through - * a series of smaller modular functions or operations. The series is called a - * composition of functions, or a function composition. When a collection of - * data flows through a function composition, it becomes a collection pipeline. - * Function Composition and Collection Pipeline are two design patterns - * frequently used in functional-style programming. - * + * a series of smaller modular functions or operations. The series is called a composition of + * functions, or a function composition. When a collection of data flows through a function + * composition, it becomes a collection pipeline. Function Composition and Collection Pipeline are + * two design patterns frequently used in functional-style programming. + * *

Instead of passing a lambda expression to the map method, we passed the - * method reference Car::getModel. Likewise, instead of passing the lambda - * expression car -> car.getYear() to the comparing method, we passed the method - * reference Car::getYear. Method references are short, concise, and expressive. - * It is best to use them wherever possible. - * + * method reference Car::getModel. Likewise, instead of passing the lambda expression car -> + * car.getYear() to the comparing method, we passed the method reference Car::getYear. Method + * references are short, concise, and expressive. It is best to use them wherever possible. */ public class FunctionalProgramming { private FunctionalProgramming() { @@ -51,35 +48,35 @@ public class FunctionalProgramming { /** * Method to get models using for collection pipeline. - * + * * @param cars {@link List} of {@link Car} to be used for filtering * @return {@link List} of {@link String} representing models built after year 2000 */ public static List getModelsAfter2000(List cars) { return cars.stream().filter(car -> car.getYear() > 2000) - .sorted(Comparator.comparing(Car::getYear)) - .map(Car::getModel).collect(Collectors.toList()); + .sorted(Comparator.comparing(Car::getYear)) + .map(Car::getModel).collect(Collectors.toList()); } - + /** - * Method to group cars by category using groupingBy - * + * Method to group cars by category using groupingBy. + * * @param cars {@link List} of {@link Car} to be used for grouping * @return {@link Map} with category as key and cars belonging to that category as value */ public static Map> getGroupingOfCarsByCategory(List cars) { return cars.stream().collect(Collectors.groupingBy(Car::getCategory)); } - + /** - * Method to get all Sedan cars belonging to a group of persons sorted by year of manufacture - * + * Method to get all Sedan cars belonging to a group of persons sorted by year of manufacture. + * * @param persons {@link List} of {@link Person} to be used * @return {@link List} of {@link Car} to belonging to the group */ public static List getSedanCarsOwnedSortedByDate(List persons) { return persons.stream().map(Person::getCars).flatMap(List::stream) - .filter(car -> Category.SEDAN.equals(car.getCategory())) - .sorted(Comparator.comparing(Car::getYear)).collect(Collectors.toList()); + .filter(car -> Category.SEDAN.equals(car.getCategory())) + .sorted(Comparator.comparing(Car::getYear)).collect(Collectors.toList()); } } diff --git a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/ImperativeProgramming.java b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/ImperativeProgramming.java index 01d095e96..a587e9c37 100644 --- a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/ImperativeProgramming.java +++ b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/ImperativeProgramming.java @@ -31,23 +31,20 @@ import java.util.List; import java.util.Map; /** - * Imperative-style programming to iterate over the list and get the names of - * cars made later than the year 2000. We then sort the models in ascending - * order by year. - * + * Imperative-style programming to iterate over the list and get the names of cars made later than + * the year 2000. We then sort the models in ascending order by year. + * *

As you can see, there's a lot of looping in this code. First, the - * getModelsAfter2000UsingFor method takes a list of cars as its parameter. It - * extracts or filters out cars made after the year 2000, putting them into a - * new list named carsSortedByYear. Next, it sorts that list in ascending order - * by year-of-make. Finally, it loops through the list carsSortedByYear to get - * the model names and returns them in a list. - * + * getModelsAfter2000UsingFor method takes a list of cars as its parameter. It extracts or filters + * out cars made after the year 2000, putting them into a new list named carsSortedByYear. Next, it + * sorts that list in ascending order by year-of-make. Finally, it loops through the list + * carsSortedByYear to get the model names and returns them in a list. + * *

This short example demonstrates what I call the effect of statements. While - * functions and methods in general can be used as expressions, the {@link Collections} - * sort method doesn't return a result. Because it is used as a statement, it - * mutates the list given as argument. Both of the for loops also mutate lists - * as they iterate. Being statements, that's just how these elements work. As a - * result, the code contains unnecessary garbage variables + * functions and methods in general can be used as expressions, the {@link Collections} sort method + * doesn't return a result. Because it is used as a statement, it mutates the list given as + * argument. Both of the for loops also mutate lists as they iterate. Being statements, that's just + * how these elements work. As a result, the code contains unnecessary garbage variables */ public class ImperativeProgramming { private ImperativeProgramming() { @@ -55,6 +52,7 @@ public class ImperativeProgramming { /** * Method to return the car models built after year 2000 using for loops. + * * @param cars {@link List} of {@link Car} to iterate over * @return {@link List} of {@link String} of car models built after year 2000 */ @@ -80,16 +78,16 @@ public class ImperativeProgramming { return models; } - + /** - * Method to group cars by category using for loops - * + * Method to group cars by category using for loops. + * * @param cars {@link List} of {@link Car} to be used for grouping * @return {@link Map} with category as key and cars belonging to that category as value */ public static Map> getGroupingOfCarsByCategory(List cars) { Map> groupingByCategory = new HashMap<>(); - for (Car car: cars) { + for (Car car : cars) { if (groupingByCategory.containsKey(car.getCategory())) { groupingByCategory.get(car.getCategory()).add(car); } else { @@ -100,33 +98,34 @@ public class ImperativeProgramming { } return groupingByCategory; } - + /** - * Method to get all Sedan cars belonging to a group of persons sorted by year of manufacture using for loops - * + * Method to get all Sedan cars belonging to a group of persons sorted by year of manufacture + * using for loops. + * * @param persons {@link List} of {@link Person} to be used * @return {@link List} of {@link Car} to belonging to the group */ public static List getSedanCarsOwnedSortedByDate(List persons) { List cars = new ArrayList<>(); - for (Person person: persons) { + for (Person person : persons) { cars.addAll(person.getCars()); } - + List sedanCars = new ArrayList<>(); - for (Car car: cars) { + for (Car car : cars) { if (Category.SEDAN.equals(car.getCategory())) { sedanCars.add(car); } } - + sedanCars.sort(new Comparator() { @Override public int compare(Car o1, Car o2) { return o1.getYear() - o2.getYear(); } }); - + return sedanCars; } } diff --git a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Person.java b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Person.java index 9bf01052a..2e564b701 100644 --- a/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Person.java +++ b/collection-pipeline/src/main/java/com/iluwatar/collectionpipeline/Person.java @@ -33,6 +33,7 @@ public class Person { /** * Constructor to create an instance of person. + * * @param cars the list of cars owned */ public Person(List cars) { diff --git a/collection-pipeline/src/test/java/com/iluwatar/collectionpipeline/AppTest.java b/collection-pipeline/src/test/java/com/iluwatar/collectionpipeline/AppTest.java index 6bc035920..1fa27ec4d 100644 --- a/collection-pipeline/src/test/java/com/iluwatar/collectionpipeline/AppTest.java +++ b/collection-pipeline/src/test/java/com/iluwatar/collectionpipeline/AppTest.java @@ -23,14 +23,13 @@ package com.iluwatar.collectionpipeline; -import org.junit.jupiter.api.Test; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; +import static org.junit.jupiter.api.Assertions.assertEquals; import java.util.List; import java.util.Map; - -import static org.junit.jupiter.api.Assertions.assertEquals; +import org.junit.jupiter.api.Test; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; /** * Tests that Collection Pipeline methods work as expected. @@ -39,35 +38,35 @@ public class AppTest { private static final Logger LOGGER = LoggerFactory.getLogger(AppTest.class); private List cars = CarFactory.createCars(); - + @Test public void testGetModelsAfter2000UsingFor() { var models = ImperativeProgramming.getModelsAfter2000(cars); assertEquals(List.of("Avenger", "Wrangler", "Focus", "Cascada"), models); } - + @Test public void testGetModelsAfter2000UsingPipeline() { var models = FunctionalProgramming.getModelsAfter2000(cars); assertEquals(List.of("Avenger", "Wrangler", "Focus", "Cascada"), models); } - + @Test public void testGetGroupingOfCarsByCategory() { var modelsExpected = Map.of( - Category.CONVERTIBLE, List.of(new Car("Buick", "Cascada", 2016, Category.CONVERTIBLE), - new Car("Chevrolet", "Geo Metro", 1992, Category.CONVERTIBLE)), - Category.SEDAN, List.of(new Car("Dodge", "Avenger", 2010, Category.SEDAN), - new Car("Ford", "Focus", 2012, Category.SEDAN)), - Category.JEEP, List.of(new Car("Jeep", "Wrangler", 2011, Category.JEEP), - new Car("Jeep", "Comanche", 1990, Category.JEEP))); + Category.CONVERTIBLE, List.of(new Car("Buick", "Cascada", 2016, Category.CONVERTIBLE), + new Car("Chevrolet", "Geo Metro", 1992, Category.CONVERTIBLE)), + Category.SEDAN, List.of(new Car("Dodge", "Avenger", 2010, Category.SEDAN), + new Car("Ford", "Focus", 2012, Category.SEDAN)), + Category.JEEP, List.of(new Car("Jeep", "Wrangler", 2011, Category.JEEP), + new Car("Jeep", "Comanche", 1990, Category.JEEP))); var modelsFunctional = FunctionalProgramming.getGroupingOfCarsByCategory(cars); var modelsImperative = ImperativeProgramming.getGroupingOfCarsByCategory(cars); LOGGER.info("Category " + modelsFunctional); assertEquals(modelsExpected, modelsFunctional); assertEquals(modelsExpected, modelsImperative); } - + @Test public void testGetSedanCarsOwnedSortedByDate() { var john = new Person(cars); diff --git a/command/src/main/java/com/iluwatar/command/App.java b/command/src/main/java/com/iluwatar/command/App.java index 39e59077e..8e7ee31a8 100644 --- a/command/src/main/java/com/iluwatar/command/App.java +++ b/command/src/main/java/com/iluwatar/command/App.java @@ -24,31 +24,28 @@ package com.iluwatar.command; /** - * * The Command pattern is a behavioral design pattern in which an object is used to encapsulate all * information needed to perform an action or trigger an event at a later time. This information * includes the method name, the object that owns the method and values for the method parameters. - *

- * Four terms always associated with the command pattern are command, receiver, invoker and client. - * A command object (spell) knows about the receiver (target) and invokes a method of the receiver. - * Values for parameters of the receiver method are stored in the command. The receiver then does - * the work. An invoker object (wizard) knows how to execute a command, and optionally does - * bookkeeping about the command execution. The invoker does not know anything about a concrete + * + *

Four terms always associated with the command pattern are command, receiver, invoker and + * client. A command object (spell) knows about the receiver (target) and invokes a method of the + * receiver. Values for parameters of the receiver method are stored in the command. The receiver + * then does the work. An invoker object (wizard) knows how to execute a command, and optionally + * does bookkeeping about the command execution. The invoker does not know anything about a concrete * command, it knows only about command interface. Both an invoker object and several command * objects are held by a client object (app). The client decides which commands to execute at which * points. To execute a command, it passes the command object to the invoker object. - *

- * In other words, in this example the wizard casts spells on the goblin. The wizard keeps track of - * the previous spells cast, so it is easy to undo them. In addition, the wizard keeps track of the - * spells undone, so they can be redone. - * - * + * + *

In other words, in this example the wizard casts spells on the goblin. The wizard keeps track + * of the previous spells cast, so it is easy to undo them. In addition, the wizard keeps track of + * the spells undone, so they can be redone. */ public class App { /** - * Program entry point - * + * Program entry point. + * * @param args command line args */ public static void main(String[] args) { diff --git a/command/src/main/java/com/iluwatar/command/Command.java b/command/src/main/java/com/iluwatar/command/Command.java index b5854f6be..85deff74e 100644 --- a/command/src/main/java/com/iluwatar/command/Command.java +++ b/command/src/main/java/com/iluwatar/command/Command.java @@ -24,9 +24,7 @@ package com.iluwatar.command; /** - * * Interface for Commands. - * */ public abstract class Command { diff --git a/command/src/main/java/com/iluwatar/command/Goblin.java b/command/src/main/java/com/iluwatar/command/Goblin.java index b2c0d75d0..72ddc43b5 100644 --- a/command/src/main/java/com/iluwatar/command/Goblin.java +++ b/command/src/main/java/com/iluwatar/command/Goblin.java @@ -24,9 +24,7 @@ package com.iluwatar.command; /** - * - * Goblin is the target of the spells - * + * Goblin is the target of the spells. */ public class Goblin extends Target { diff --git a/command/src/main/java/com/iluwatar/command/InvisibilitySpell.java b/command/src/main/java/com/iluwatar/command/InvisibilitySpell.java index bdbc54889..3e0f7bbf4 100644 --- a/command/src/main/java/com/iluwatar/command/InvisibilitySpell.java +++ b/command/src/main/java/com/iluwatar/command/InvisibilitySpell.java @@ -24,9 +24,7 @@ package com.iluwatar.command; /** - * - * InvisibilitySpell is a concrete command - * + * InvisibilitySpell is a concrete command. */ public class InvisibilitySpell extends Command { diff --git a/command/src/main/java/com/iluwatar/command/ShrinkSpell.java b/command/src/main/java/com/iluwatar/command/ShrinkSpell.java index 81f04d407..6bbc339f4 100644 --- a/command/src/main/java/com/iluwatar/command/ShrinkSpell.java +++ b/command/src/main/java/com/iluwatar/command/ShrinkSpell.java @@ -24,9 +24,7 @@ package com.iluwatar.command; /** - * - * ShrinkSpell is a concrete command - * + * ShrinkSpell is a concrete command. */ public class ShrinkSpell extends Command { diff --git a/command/src/main/java/com/iluwatar/command/Size.java b/command/src/main/java/com/iluwatar/command/Size.java index a10fb84bc..ae327d8b1 100644 --- a/command/src/main/java/com/iluwatar/command/Size.java +++ b/command/src/main/java/com/iluwatar/command/Size.java @@ -24,9 +24,7 @@ package com.iluwatar.command; /** - * * Enumeration for target size. - * */ public enum Size { diff --git a/command/src/main/java/com/iluwatar/command/Target.java b/command/src/main/java/com/iluwatar/command/Target.java index 8bf652e6c..f5ac4344c 100644 --- a/command/src/main/java/com/iluwatar/command/Target.java +++ b/command/src/main/java/com/iluwatar/command/Target.java @@ -27,9 +27,7 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** - * * Base class for spell targets. - * */ public abstract class Target { @@ -59,7 +57,7 @@ public abstract class Target { public abstract String toString(); /** - * Print status + * Print status. */ public void printStatus() { LOGGER.info("{}, [size={}] [visibility={}]", this, getSize(), getVisibility()); diff --git a/command/src/main/java/com/iluwatar/command/Visibility.java b/command/src/main/java/com/iluwatar/command/Visibility.java index a8ed73052..3c48990a0 100644 --- a/command/src/main/java/com/iluwatar/command/Visibility.java +++ b/command/src/main/java/com/iluwatar/command/Visibility.java @@ -24,9 +24,7 @@ package com.iluwatar.command; /** - * * Enumeration for target visibility. - * */ public enum Visibility { diff --git a/command/src/main/java/com/iluwatar/command/Wizard.java b/command/src/main/java/com/iluwatar/command/Wizard.java index a56c56505..fcd6e3a5b 100644 --- a/command/src/main/java/com/iluwatar/command/Wizard.java +++ b/command/src/main/java/com/iluwatar/command/Wizard.java @@ -23,16 +23,13 @@ package com.iluwatar.command; +import java.util.Deque; +import java.util.LinkedList; import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import java.util.Deque; -import java.util.LinkedList; - /** - * - * Wizard is the invoker of the commands - * + * Wizard is the invoker of the commands. */ public class Wizard { @@ -46,7 +43,7 @@ public class Wizard { } /** - * Cast spell + * Cast spell. */ public void castSpell(Command command, Target target) { LOGGER.info("{} casts {} at {}", this, command, target); @@ -55,7 +52,7 @@ public class Wizard { } /** - * Undo last spell + * Undo last spell. */ public void undoLastSpell() { if (!undoStack.isEmpty()) { @@ -67,7 +64,7 @@ public class Wizard { } /** - * Redo last spell + * Redo last spell. */ public void redoLastSpell() { if (!redoStack.isEmpty()) { diff --git a/commander/src/main/java/com/iluwatar/commander/AppEmployeeDbFailCases.java b/commander/src/main/java/com/iluwatar/commander/AppEmployeeDbFailCases.java index b488056a6..84297f828 100644 --- a/commander/src/main/java/com/iluwatar/commander/AppEmployeeDbFailCases.java +++ b/commander/src/main/java/com/iluwatar/commander/AppEmployeeDbFailCases.java @@ -31,16 +31,15 @@ import com.iluwatar.commander.messagingservice.MessagingDatabase; import com.iluwatar.commander.messagingservice.MessagingService; import com.iluwatar.commander.paymentservice.PaymentDatabase; import com.iluwatar.commander.paymentservice.PaymentService; +import com.iluwatar.commander.queue.QueueDatabase; import com.iluwatar.commander.shippingservice.ShippingDatabase; import com.iluwatar.commander.shippingservice.ShippingService; -import com.iluwatar.commander.queue.QueueDatabase; /** - * AppEmployeeDbFailCases class looks at possible cases when Employee handle service is + * AppEmployeeDbFailCases class looks at possible cases when Employee handle service is * available/unavailable. */ - -public class AppEmployeeDbFailCases { +public class AppEmployeeDbFailCases { final int numOfRetries = 3; final long retryDuration = 30000; final long queueTime = 240000; //4 mins @@ -50,33 +49,40 @@ public class AppEmployeeDbFailCases { final long employeeTime = 240000; //4 mins void employeeDatabaseUnavailableCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); ShippingService ss = new ShippingService(new ShippingDatabase()); MessagingService ms = new MessagingService(new MessagingDatabase()); - EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); - QueueDatabase qdb = new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + EmployeeHandle eh = + new EmployeeHandle(new EmployeeDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); + QueueDatabase qdb = + new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException()); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); } void employeeDbSuccessCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase()); - ShippingService ss = new ShippingService(new ShippingDatabase(), new ItemUnavailableException()); + PaymentService ps = new PaymentService(new PaymentDatabase()); + ShippingService ss = + new ShippingService(new ShippingDatabase(), new ItemUnavailableException()); MessagingService ms = new MessagingService(new MessagingDatabase()); - EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); + EmployeeHandle eh = + new EmployeeHandle(new EmployeeDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -87,7 +93,7 @@ public class AppEmployeeDbFailCases { * * @param args command line args */ - + public static void main(String[] args) throws Exception { AppEmployeeDbFailCases aefc = new AppEmployeeDbFailCases(); //aefc.employeeDatabaseUnavailableCase(); diff --git a/commander/src/main/java/com/iluwatar/commander/AppMessagingFailCases.java b/commander/src/main/java/com/iluwatar/commander/AppMessagingFailCases.java index a6010229e..d644d1c1f 100644 --- a/commander/src/main/java/com/iluwatar/commander/AppMessagingFailCases.java +++ b/commander/src/main/java/com/iluwatar/commander/AppMessagingFailCases.java @@ -30,12 +30,12 @@ import com.iluwatar.commander.messagingservice.MessagingDatabase; import com.iluwatar.commander.messagingservice.MessagingService; import com.iluwatar.commander.paymentservice.PaymentDatabase; import com.iluwatar.commander.paymentservice.PaymentService; +import com.iluwatar.commander.queue.QueueDatabase; import com.iluwatar.commander.shippingservice.ShippingDatabase; import com.iluwatar.commander.shippingservice.ShippingService; -import com.iluwatar.commander.queue.QueueDatabase; /** - * AppMessagingFailCases class looks at possible cases when Messaging service is + * AppMessagingFailCases class looks at possible cases when Messaging service is * available/unavailable. */ @@ -50,15 +50,17 @@ public class AppMessagingFailCases { void messagingDatabaseUnavailableCasePaymentSuccess() throws Exception { //rest is successful - PaymentService ps = new PaymentService(new PaymentDatabase()); + PaymentService ps = new PaymentService(new PaymentDatabase()); ShippingService ss = new ShippingService(new ShippingDatabase()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -66,40 +68,52 @@ public class AppMessagingFailCases { void messagingDatabaseUnavailableCasePaymentError() throws Exception { //rest is successful - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); ShippingService ss = new ShippingService(new ShippingDatabase()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); } - void messagingDatabaseUnavailableCasePaymentFailure() throws Exception { + void messagingDatabaseUnavailableCasePaymentFailure() throws Exception { //rest is successful - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); ShippingService ss = new ShippingService(new ShippingDatabase()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); - QueueDatabase qdb = new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration,queueTime,queueTaskTime, - paymentTime,messageTime,employeeTime); + QueueDatabase qdb = + new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException()); + Commander c = + new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, queueTime, queueTaskTime, + paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -107,16 +121,19 @@ public class AppMessagingFailCases { void messagingSuccessCase() throws Exception { //done here - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); ShippingService ss = new ShippingService(new ShippingDatabase()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -127,7 +144,7 @@ public class AppMessagingFailCases { * * @param args command line args */ - + public static void main(String[] args) throws Exception { AppMessagingFailCases amfc = new AppMessagingFailCases(); //amfc.messagingDatabaseUnavailableCasePaymentSuccess(); diff --git a/commander/src/main/java/com/iluwatar/commander/AppPaymentFailCases.java b/commander/src/main/java/com/iluwatar/commander/AppPaymentFailCases.java index 86fd5a83c..4e65b1d28 100644 --- a/commander/src/main/java/com/iluwatar/commander/AppPaymentFailCases.java +++ b/commander/src/main/java/com/iluwatar/commander/AppPaymentFailCases.java @@ -31,13 +31,12 @@ import com.iluwatar.commander.messagingservice.MessagingDatabase; import com.iluwatar.commander.messagingservice.MessagingService; import com.iluwatar.commander.paymentservice.PaymentDatabase; import com.iluwatar.commander.paymentservice.PaymentService; +import com.iluwatar.commander.queue.QueueDatabase; import com.iluwatar.commander.shippingservice.ShippingDatabase; import com.iluwatar.commander.shippingservice.ShippingService; -import com.iluwatar.commander.queue.QueueDatabase; /** - * AppPaymentFailCases class looks at possible cases when Payment service is - * available/unavailable. + * AppPaymentFailCases class looks at possible cases when Payment service is available/unavailable. */ public class AppPaymentFailCases { @@ -50,14 +49,16 @@ public class AppPaymentFailCases { final long employeeTime = 240000; //4 mins void paymentNotPossibleCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new PaymentDetailsErrorException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new PaymentDetailsErrorException()); ShippingService ss = new ShippingService(new ShippingDatabase()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(new DatabaseUnavailableException()); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -65,15 +66,17 @@ public class AppPaymentFailCases { void paymentDatabaseUnavailableCase() throws Exception { //rest is successful - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); ShippingService ss = new ShippingService(new ShippingDatabase()); MessagingService ms = new MessagingService(new MessagingDatabase()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -81,14 +84,16 @@ public class AppPaymentFailCases { void paymentSuccessCase() throws Exception { //goes to message after 2 retries maybe - rest is successful for now - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); ShippingService ss = new ShippingService(new ShippingDatabase()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(new DatabaseUnavailableException()); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -99,7 +104,7 @@ public class AppPaymentFailCases { * * @param args command line args */ - + public static void main(String[] args) throws Exception { AppPaymentFailCases apfc = new AppPaymentFailCases(); //apfc.paymentNotPossibleCase(); diff --git a/commander/src/main/java/com/iluwatar/commander/AppQueueFailCases.java b/commander/src/main/java/com/iluwatar/commander/AppQueueFailCases.java index f8c3548b2..34ed81c0f 100644 --- a/commander/src/main/java/com/iluwatar/commander/AppQueueFailCases.java +++ b/commander/src/main/java/com/iluwatar/commander/AppQueueFailCases.java @@ -31,13 +31,12 @@ import com.iluwatar.commander.messagingservice.MessagingDatabase; import com.iluwatar.commander.messagingservice.MessagingService; import com.iluwatar.commander.paymentservice.PaymentDatabase; import com.iluwatar.commander.paymentservice.PaymentService; +import com.iluwatar.commander.queue.QueueDatabase; import com.iluwatar.commander.shippingservice.ShippingDatabase; import com.iluwatar.commander.shippingservice.ShippingService; -import com.iluwatar.commander.queue.QueueDatabase; /** - * AppQueueFailCases class looks at possible cases when Queue Database is - * available/unavailable. + * AppQueueFailCases class looks at possible cases when Queue Database is available/unavailable. */ public class AppQueueFailCases { @@ -50,71 +49,87 @@ public class AppQueueFailCases { final long employeeTime = 240000; //4 mins void queuePaymentTaskDatabaseUnavailableCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); ShippingService ss = new ShippingService(new ShippingDatabase()); MessagingService ms = new MessagingService(new MessagingDatabase()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); - QueueDatabase qdb = new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + QueueDatabase qdb = + new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException()); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); } void queueMessageTaskDatabaseUnavailableCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase()); + PaymentService ps = new PaymentService(new PaymentDatabase()); ShippingService ss = new ShippingService(new ShippingDatabase()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); - QueueDatabase qdb = new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + QueueDatabase qdb = + new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException()); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); } void queueEmployeeDbTaskDatabaseUnavailableCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase()); - ShippingService ss = new ShippingService(new ShippingDatabase(), new ItemUnavailableException()); + PaymentService ps = new PaymentService(new PaymentDatabase()); + ShippingService ss = + new ShippingService(new ShippingDatabase(), new ItemUnavailableException()); MessagingService ms = new MessagingService(new MessagingDatabase()); - EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); - QueueDatabase qdb = new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + EmployeeHandle eh = + new EmployeeHandle(new EmployeeDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); + QueueDatabase qdb = + new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException()); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); } void queueSuccessCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); ShippingService ss = new ShippingService(new ShippingDatabase()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); - QueueDatabase qdb = new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException()); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + QueueDatabase qdb = + new QueueDatabase(new DatabaseUnavailableException(), new DatabaseUnavailableException()); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); diff --git a/commander/src/main/java/com/iluwatar/commander/AppShippingFailCases.java b/commander/src/main/java/com/iluwatar/commander/AppShippingFailCases.java index b65f4fa4e..a055ba699 100644 --- a/commander/src/main/java/com/iluwatar/commander/AppShippingFailCases.java +++ b/commander/src/main/java/com/iluwatar/commander/AppShippingFailCases.java @@ -32,12 +32,12 @@ import com.iluwatar.commander.messagingservice.MessagingDatabase; import com.iluwatar.commander.messagingservice.MessagingService; import com.iluwatar.commander.paymentservice.PaymentDatabase; import com.iluwatar.commander.paymentservice.PaymentService; +import com.iluwatar.commander.queue.QueueDatabase; import com.iluwatar.commander.shippingservice.ShippingDatabase; import com.iluwatar.commander.shippingservice.ShippingService; -import com.iluwatar.commander.queue.QueueDatabase; /** - * AppShippingFailCases class looks at possible cases when Shipping service is + * AppShippingFailCases class looks at possible cases when Shipping service is * available/unavailable. */ @@ -51,26 +51,28 @@ public class AppShippingFailCases { final long employeeTime = 240000; //4 mins void itemUnavailableCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase()); - ShippingService ss = new ShippingService(new ShippingDatabase(), new ItemUnavailableException()); + PaymentService ps = new PaymentService(new PaymentDatabase()); + ShippingService ss = + new ShippingService(new ShippingDatabase(), new ItemUnavailableException()); MessagingService ms = new MessagingService(new MessagingDatabase()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); } void shippingNotPossibleCase() throws Exception { - PaymentService ps = new PaymentService(new PaymentDatabase()); - ShippingService ss = new ShippingService(new ShippingDatabase(), new ShippingNotPossibleException()); + PaymentService ps = new PaymentService(new PaymentDatabase()); + ShippingService ss = + new ShippingService(new ShippingDatabase(), new ShippingNotPossibleException()); MessagingService ms = new MessagingService(new MessagingDatabase()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -78,15 +80,17 @@ public class AppShippingFailCases { void shippingDatabaseUnavailableCase() throws Exception { //rest is successful - PaymentService ps = new PaymentService(new PaymentDatabase()); - ShippingService ss = new ShippingService(new ShippingDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException(), new DatabaseUnavailableException(), - new DatabaseUnavailableException(), new DatabaseUnavailableException()); + PaymentService ps = new PaymentService(new PaymentDatabase()); + ShippingService ss = + new ShippingService(new ShippingDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); MessagingService ms = new MessagingService(new MessagingDatabase()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); @@ -94,25 +98,28 @@ public class AppShippingFailCases { void shippingSuccessCase() throws Exception { //goes to payment after 2 retries maybe - rest is successful for now - PaymentService ps = new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException()); - ShippingService ss = new ShippingService(new ShippingDatabase(), new DatabaseUnavailableException(), - new DatabaseUnavailableException()); - MessagingService ms = new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException()); + PaymentService ps = + new PaymentService(new PaymentDatabase(), new DatabaseUnavailableException()); + ShippingService ss = + new ShippingService(new ShippingDatabase(), new DatabaseUnavailableException(), + new DatabaseUnavailableException()); + MessagingService ms = + new MessagingService(new MessagingDatabase(), new DatabaseUnavailableException()); EmployeeHandle eh = new EmployeeHandle(new EmployeeDatabase()); QueueDatabase qdb = new QueueDatabase(); - Commander c = new Commander(eh,ps,ss,ms,qdb,numOfRetries,retryDuration, - queueTime,queueTaskTime,paymentTime,messageTime,employeeTime); + Commander c = new Commander(eh, ps, ss, ms, qdb, numOfRetries, retryDuration, + queueTime, queueTaskTime, paymentTime, messageTime, employeeTime); User user = new User("Jim", "ABCD"); Order order = new Order(user, "book", 10f); c.placeOrder(order); } - + /** * Program entry point. * * @param args command line args */ - + public static void main(String[] args) throws Exception { AppShippingFailCases asfc = new AppShippingFailCases(); //asfc.itemUnavailableCase(); diff --git a/commander/src/main/java/com/iluwatar/commander/Commander.java b/commander/src/main/java/com/iluwatar/commander/Commander.java index d161f7b9f..0c0989ade 100644 --- a/commander/src/main/java/com/iluwatar/commander/Commander.java +++ b/commander/src/main/java/com/iluwatar/commander/Commander.java @@ -23,53 +23,51 @@ package com.iluwatar.commander; -import java.util.ArrayList; +import com.iluwatar.commander.Order.MessageSent; +import com.iluwatar.commander.Order.PaymentStatus; import com.iluwatar.commander.employeehandle.EmployeeHandle; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; import com.iluwatar.commander.exceptions.ItemUnavailableException; import com.iluwatar.commander.exceptions.PaymentDetailsErrorException; import com.iluwatar.commander.exceptions.ShippingNotPossibleException; import com.iluwatar.commander.messagingservice.MessagingService; -import com.iluwatar.commander.Order.MessageSent; -import com.iluwatar.commander.Order.PaymentStatus; import com.iluwatar.commander.paymentservice.PaymentService; import com.iluwatar.commander.queue.QueueDatabase; import com.iluwatar.commander.queue.QueueTask; import com.iluwatar.commander.queue.QueueTask.TaskType; import com.iluwatar.commander.shippingservice.ShippingService; +import java.util.ArrayList; import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** - *

Commander pattern is used to handle all issues that can come up while making a - * distributed transaction. The idea is to have a commander, which coordinates the - * execution of all instructions and ensures proper completion using retries and - * taking care of idempotence. By queueing instructions while they haven't been done, - * we can ensure a state of 'eventual consistency'.

+ *

Commander pattern is used to handle all issues that can come up while making a + * distributed transaction. The idea is to have a commander, which coordinates the execution of all + * instructions and ensures proper completion using retries and taking care of idempotence. By + * queueing instructions while they haven't been done, we can ensure a state of 'eventual + * consistency'.

*

In our example, we have an e-commerce application. When the user places an order, - * the shipping service is intimated first. If the service does not respond for some - * reason, the order is not placed. If response is received, the commander then calls - * for the payment service to be intimated. If this fails, the shipping still takes - * place (order converted to COD) and the item is queued. If the queue is also found - * to be unavailable, the payment is noted to be not done and this is added to an - * employee database. Three types of messages are sent to the user - one, if payment - * succeeds; two, if payment fails definitively; and three, if payment fails in the - * first attempt. If the message is not sent, this is also queued and is added to employee - * db. We also have a time limit for each instruction to be completed, after which, the - * instruction is not executed, thereby ensuring that resources are not held for too long. - * In the rare occasion in which everything fails, an individual would have to step in to - * figure out how to solve the issue.

+ * the shipping service is intimated first. If the service does not respond for some reason, the + * order is not placed. If response is received, the commander then calls for the payment service to + * be intimated. If this fails, the shipping still takes place (order converted to COD) and the item + * is queued. If the queue is also found to be unavailable, the payment is noted to be not done and + * this is added to an employee database. Three types of messages are sent to the user - one, if + * payment succeeds; two, if payment fails definitively; and three, if payment fails in the first + * attempt. If the message is not sent, this is also queued and is added to employee db. We also + * have a time limit for each instruction to be completed, after which, the instruction is not + * executed, thereby ensuring that resources are not held for too long. In the rare occasion in + * which everything fails, an individual would have to step in to figure out how to solve the + * issue.

*

We have abstract classes {@link Database} and {@link Service} which are extended - * by all the databases and services. Each service has a database to be updated, and - * receives request from an outside user (the {@link Commander} class here). There are - * 5 microservices - {@link ShippingService}, {@link PaymentService}, {@link MessagingService}, - * {@link EmployeeHandle} and a {@link QueueDatabase}. We use retries to execute any - * instruction using {@link Retry} class, and idempotence is ensured by going through some - * checks before making requests to services and making change in {@link Order} class fields - * if request succeeds or definitively fails. There are 5 classes - - * {@link AppShippingFailCases}, {@link AppPaymentFailCases}, {@link AppMessagingFailCases}, - * {@link AppQueueFailCases} and {@link AppEmployeeDbFailCases}, which look at the different - * scenarios that may be encountered during the placing of an order.

+ * by all the databases and services. Each service has a database to be updated, and receives + * request from an outside user (the {@link Commander} class here). There are 5 microservices - + * {@link ShippingService}, {@link PaymentService}, {@link MessagingService}, {@link EmployeeHandle} + * and a {@link QueueDatabase}. We use retries to execute any instruction using {@link Retry} class, + * and idempotence is ensured by going through some checks before making requests to services and + * making change in {@link Order} class fields if request succeeds or definitively fails. There are + * 5 classes - {@link AppShippingFailCases}, {@link AppPaymentFailCases}, {@link + * AppMessagingFailCases}, {@link AppQueueFailCases} and {@link AppEmployeeDbFailCases}, which look + * at the different scenarios that may be encountered during the placing of an order.

*/ public class Commander { @@ -86,17 +84,18 @@ public class Commander { private final long queueTaskTime; private final long paymentTime; private final long messageTime; - private final long employeeTime; + private final long employeeTime; private boolean finalSiteMsgShown; static final Logger LOG = LoggerFactory.getLogger(Commander.class); //we could also have another db where it stores all orders - - Commander(EmployeeHandle empDb, PaymentService pService, ShippingService sService, - MessagingService mService, QueueDatabase qdb, int numOfRetries, long retryDuration, - long queueTime, long queueTaskTime, long paymentTime, long messageTime, long employeeTime) { - this.paymentService = pService; - this.shippingService = sService; - this.messagingService = mService; + + Commander(EmployeeHandle empDb, PaymentService paymentService, ShippingService shippingService, + MessagingService messagingService, QueueDatabase qdb, int numOfRetries, + long retryDuration, long queueTime, long queueTaskTime, long paymentTime, + long messageTime, long employeeTime) { + this.paymentService = paymentService; + this.shippingService = shippingService; + this.messagingService = messagingService; this.employeeDb = empDb; this.queue = qdb; this.numOfRetries = numOfRetries; @@ -106,7 +105,7 @@ public class Commander { this.paymentTime = paymentTime; this.messageTime = messageTime; this.employeeTime = employeeTime; - this.finalSiteMsgShown = false; + this.finalSiteMsgShown = false; } void placeOrder(Order order) throws Exception { @@ -118,40 +117,43 @@ public class Commander { Retry.Operation op = (l) -> { if (!l.isEmpty()) { if (DatabaseUnavailableException.class.isAssignableFrom(l.get(0).getClass())) { - LOG.debug("Order " + order.id + ": Error in connecting to shipping service, trying again.."); + LOG.debug("Order " + order.id + ": Error in connecting to shipping service, " + + "trying again.."); } else { LOG.debug("Order " + order.id + ": Error in creating shipping request.."); } throw l.remove(0); - } - String transactionId = shippingService.receiveRequest(order.item, order.user.address); + } + String transactionId = shippingService.receiveRequest(order.item, order.user.address); //could save this transaction id in a db too - LOG.info("Order " + order.id + ": Shipping placed successfully, transaction id: " + transactionId); + LOG.info("Order " + order.id + ": Shipping placed successfully, transaction id: " + + transactionId); LOG.info("Order has been placed and will be shipped to you. Please wait while we make your" - + " payment... "); - sendPaymentRequest(order); - return; + + " payment... "); + sendPaymentRequest(order); + return; }; - Retry.HandleErrorIssue handleError = (o,err) -> { + Retry.HandleErrorIssue handleError = (o, err) -> { if (ShippingNotPossibleException.class.isAssignableFrom(err.getClass())) { - LOG.info("Shipping is currently not possible to your address. We are working on the problem " - + "and will get back to you asap."); + LOG.info("Shipping is currently not possible to your address. We are working on the problem" + + " and will get back to you asap."); finalSiteMsgShown = true; - LOG.info("Order " + order.id + ": Shipping not possible to address, trying to add problem to employee db.."); + LOG.info("Order " + order.id + ": Shipping not possible to address, trying to add problem " + + "to employee db.."); employeeHandleIssue(o); } else if (ItemUnavailableException.class.isAssignableFrom(err.getClass())) { - LOG.info("This item is currently unavailable. We will inform you as soon as the item becomes " - + "available again."); + LOG.info("This item is currently unavailable. We will inform you as soon as the item " + + "becomes available again."); finalSiteMsgShown = true; - LOG.info("Order " + order.id + ": Item " + order.item + " unavailable, trying to add problem to employee " - + "handle.."); + LOG.info("Order " + order.id + ": Item " + order.item + " unavailable, trying to add " + + "problem to employee handle.."); employeeHandleIssue(o); } else { LOG.info("Sorry, there was a problem in creating your order. Please try later."); LOG.error("Order " + order.id + ": Shipping service unavailable, order not placed.."); finalSiteMsgShown = true; } - return; + return; }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -174,28 +176,31 @@ public class Commander { Retry.Operation op = (l) -> { if (!l.isEmpty()) { if (DatabaseUnavailableException.class.isAssignableFrom(l.get(0).getClass())) { - LOG.debug("Order " + order.id + ": Error in connecting to payment service, trying again.."); + LOG.debug("Order " + order.id + ": Error in connecting to payment service," + + " trying again.."); } else { LOG.debug("Order " + order.id + ": Error in creating payment request.."); } - throw l.remove(0); - } + throw l.remove(0); + } if (order.paid.equals(PaymentStatus.Trying)) { String transactionId = paymentService.receiveRequest(order.price); - order.paid = PaymentStatus.Done; - LOG.info("Order " + order.id + ": Payment successful, transaction Id: " + transactionId); - if (!finalSiteMsgShown) { - LOG.info("Payment made successfully, thank you for shopping with us!!"); - finalSiteMsgShown = true; - } - sendSuccessMessage(order); - return; - } + order.paid = PaymentStatus.Done; + LOG.info("Order " + order.id + ": Payment successful, transaction Id: " + + transactionId); + if (!finalSiteMsgShown) { + LOG.info("Payment made successfully, thank you for shopping with us!!"); + finalSiteMsgShown = true; + } + sendSuccessMessage(order); + return; + } }; - Retry.HandleErrorIssue handleError = (o,err) -> { + Retry.HandleErrorIssue handleError = (o, err) -> { if (PaymentDetailsErrorException.class.isAssignableFrom(err.getClass())) { if (!finalSiteMsgShown) { - LOG.info("There was an error in payment. Your account/card details may have been incorrect. " + LOG.info("There was an error in payment. Your account/card details " + + "may have been incorrect. " + "Meanwhile, your order has been converted to COD and will be shipped."); finalSiteMsgShown = true; } @@ -213,15 +218,16 @@ public class Commander { LOG.warn("Order " + order.id + ": Payment error, going to queue.."); sendPaymentPossibleErrorMsg(o); } - if (o.paid.equals(PaymentStatus.Trying) && System.currentTimeMillis() - o.createdTime < paymentTime) { - QueueTask qt = new QueueTask(o, TaskType.Payment,-1); + if (o.paid.equals(PaymentStatus.Trying) && System + .currentTimeMillis() - o.createdTime < paymentTime) { + QueueTask qt = new QueueTask(o, TaskType.Payment, -1); updateQueue(qt); - } + } } catch (InterruptedException e1) { e1.printStackTrace(); - } - } - return; + } + } + return; }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -229,7 +235,7 @@ public class Commander { r.perform(list, order); } catch (Exception e1) { e1.printStackTrace(); - } + } } }); t.start(); @@ -237,17 +243,18 @@ public class Commander { private void updateQueue(QueueTask qt) throws InterruptedException { if (System.currentTimeMillis() - qt.order.createdTime >= this.queueTime) { - //since payment time is lesser than queuetime it would have already failed..additional check not needed + // since payment time is lesser than queuetime it would have already failed.. + // additional check not needed LOG.trace("Order " + qt.order.id + ": Queue time for order over, failed.."); return; } else if (qt.taskType.equals(TaskType.Payment) && !qt.order.paid.equals(PaymentStatus.Trying) || qt.taskType.equals(TaskType.Messaging) && (qt.messageType == 1 && !qt.order.messageSent.equals(MessageSent.NoneSent) - || qt.order.messageSent.equals(MessageSent.PaymentFail) + || qt.order.messageSent.equals(MessageSent.PaymentFail) || qt.order.messageSent.equals(MessageSent.PaymentSuccessful)) || qt.taskType.equals(TaskType.EmployeeDb) && qt.order.addedToEmployeeHandle) { LOG.trace("Order " + qt.order.id + ": Not queueing task since task already done.."); - return; + return; } ArrayList list = queue.exceptionsList; Thread t = new Thread(new Runnable() { @@ -256,24 +263,25 @@ public class Commander { Retry.Operation op = (list) -> { if (!list.isEmpty()) { LOG.warn("Order " + qt.order.id + ": Error in connecting to queue db, trying again.."); - throw list.remove(0); - } - queue.add(qt); - queueItems++; + throw list.remove(0); + } + queue.add(qt); + queueItems++; LOG.info("Order " + qt.order.id + ": " + qt.getType() + " task enqueued.."); tryDoingTasksInQueue(); - return; + return; }; - Retry.HandleErrorIssue handleError = (qt,err) -> { + Retry.HandleErrorIssue handleError = (qt, err) -> { if (qt.taskType.equals(TaskType.Payment)) { - qt.order.paid = PaymentStatus.NotDone; - sendPaymentFailureMessage(qt.order); - LOG.error("Order " + qt.order.id + ": Unable to enqueue payment task, payment failed.."); + qt.order.paid = PaymentStatus.NotDone; + sendPaymentFailureMessage(qt.order); + LOG.error("Order " + qt.order.id + ": Unable to enqueue payment task," + + " payment failed.."); } - LOG.error("Order " + qt.order.id + ": Unable to enqueue task of type " + qt.getType() + LOG.error("Order " + qt.order.id + ": Unable to enqueue task of type " + qt.getType() + ", trying to add to employee handle.."); employeeHandleIssue(qt.order); - return; + return; }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -281,8 +289,8 @@ public class Commander { r.perform(list, qt); } catch (Exception e1) { e1.printStackTrace(); - } - } + } + } }); t.start(); } @@ -295,13 +303,13 @@ public class Commander { Retry.Operation op = (list) -> { if (!list.isEmpty()) { LOG.warn("Error in accessing queue db to do tasks, trying again.."); - throw list.remove(0); + throw list.remove(0); } doTasksInQueue(); - return; + return; }; - Retry.HandleErrorIssue handleError = (o,err) -> { - return; + Retry.HandleErrorIssue handleError = (o, err) -> { + return; }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -309,8 +317,8 @@ public class Commander { r.perform(list, null); } catch (Exception e1) { e1.printStackTrace(); - } - } + } + } }); t2.start(); } @@ -323,14 +331,14 @@ public class Commander { Retry.Operation op = (list) -> { if (!list.isEmpty()) { LOG.warn("Error in accessing queue db to dequeue task, trying again.."); - throw list.remove(0); - } - queue.dequeue(); - queueItems--; + throw list.remove(0); + } + queue.dequeue(); + queueItems--; return; }; - Retry.HandleErrorIssue handleError = (o,err) -> { - return; + Retry.HandleErrorIssue handleError = (o, err) -> { + return; }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -338,12 +346,12 @@ public class Commander { r.perform(list, null); } catch (Exception e1) { e1.printStackTrace(); - } + } } }); t3.start(); } - + private void sendSuccessMessage(Order order) { if (System.currentTimeMillis() - order.createdTime >= this.messageTime) { LOG.trace("Order " + order.id + ": Message time for order over, returning.."); @@ -359,32 +367,35 @@ public class Commander { LOG.debug("Order " + order.id + ": Error in connecting to messaging service " + "(Payment Success msg), trying again.."); } else { - LOG.debug("Order " + order.id + ": Error in creating Payment Success messaging request.."); + LOG.debug("Order " + order.id + ": Error in creating Payment Success" + + " messaging request.."); } - throw l.remove(0); - } - if (!order.messageSent.equals(MessageSent.PaymentFail) + throw l.remove(0); + } + if (!order.messageSent.equals(MessageSent.PaymentFail) && !order.messageSent.equals(MessageSent.PaymentSuccessful)) { - String requestId = messagingService.receiveRequest(2); + String requestId = messagingService.receiveRequest(2); order.messageSent = MessageSent.PaymentSuccessful; - LOG.info("Order " + order.id + ": Payment Success message sent, request Id: " + requestId); - } - return; + LOG.info("Order " + order.id + ": Payment Success message sent," + + " request Id: " + requestId); + } + return; }; - Retry.HandleErrorIssue handleError = (o,err) -> { + Retry.HandleErrorIssue handleError = (o, err) -> { try { - if ((o.messageSent.equals(MessageSent.NoneSent) || o.messageSent.equals(MessageSent.PaymentTrying)) + if ((o.messageSent.equals(MessageSent.NoneSent) || o.messageSent + .equals(MessageSent.PaymentTrying)) && System.currentTimeMillis() - o.createdTime < messageTime) { - QueueTask qt = new QueueTask(order, TaskType.Messaging,2); + QueueTask qt = new QueueTask(order, TaskType.Messaging, 2); updateQueue(qt); - LOG.info("Order " + order.id + ": Error in sending Payment Success message, trying to " - + "queue task and add to employee handle.."); + LOG.info("Order " + order.id + ": Error in sending Payment Success message, trying to" + + " queue task and add to employee handle.."); employeeHandleIssue(order); } } catch (InterruptedException e1) { e1.printStackTrace(); - } - return; + } + return; }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -392,8 +403,8 @@ public class Commander { r.perform(list, order); } catch (Exception e1) { e1.printStackTrace(); - } - } + } + } }); t.start(); } @@ -413,32 +424,35 @@ public class Commander { LOG.debug("Order " + order.id + ": Error in connecting to messaging service " + "(Payment Failure msg), trying again.."); } else { - LOG.debug("Order " + order.id + ": Error in creating Payment Failure message request.."); + LOG.debug("Order " + order.id + ": Error in creating Payment Failure" + + " message request.."); } - throw l.remove(0); - } - if (!order.messageSent.equals(MessageSent.PaymentFail) - && !order.messageSent.equals(MessageSent.PaymentSuccessful)) { - String requestId = messagingService.receiveRequest(0); + throw l.remove(0); + } + if (!order.messageSent.equals(MessageSent.PaymentFail) + && !order.messageSent.equals(MessageSent.PaymentSuccessful)) { + String requestId = messagingService.receiveRequest(0); order.messageSent = MessageSent.PaymentFail; - LOG.info("Order " + order.id + ": Payment Failure message sent successfully, request Id: " + requestId); - } - return; + LOG.info("Order " + order.id + ": Payment Failure message sent successfully," + + " request Id: " + requestId); + } + return; }; - Retry.HandleErrorIssue handleError = (o,err) -> { - if ((o.messageSent.equals(MessageSent.NoneSent) || o.messageSent.equals(MessageSent.PaymentTrying)) + Retry.HandleErrorIssue handleError = (o, err) -> { + if ((o.messageSent.equals(MessageSent.NoneSent) || o.messageSent + .equals(MessageSent.PaymentTrying)) && System.currentTimeMillis() - o.createdTime < messageTime) { try { - QueueTask qt = new QueueTask(order, TaskType.Messaging,0); + QueueTask qt = new QueueTask(order, TaskType.Messaging, 0); updateQueue(qt); LOG.warn("Order " + order.id + ": Error in sending Payment Failure message, " + "trying to queue task and add to employee handle.."); employeeHandleIssue(o); } catch (InterruptedException e1) { e1.printStackTrace(); - } - return; - } + } + return; + } }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -446,8 +460,8 @@ public class Commander { r.perform(list, order); } catch (Exception e1) { e1.printStackTrace(); - } - } + } + } }); t.start(); } @@ -467,31 +481,35 @@ public class Commander { LOG.debug("Order " + order.id + ": Error in connecting to messaging service " + "(Payment Error msg), trying again.."); } else { - LOG.debug("Order " + order.id + ": Error in creating Payment Error messaging request.."); + LOG.debug("Order " + order.id + ": Error in creating Payment Error" + + " messaging request.."); } - throw l.remove(0); + throw l.remove(0); } - if (order.paid.equals(PaymentStatus.Trying) && order.messageSent.equals(MessageSent.NoneSent)) { - String requestId = messagingService.receiveRequest(1); - order.messageSent = MessageSent.PaymentTrying; - LOG.info("Order " + order.id + ": Payment Error message sent successfully, request Id: " + requestId); - } - return; + if (order.paid.equals(PaymentStatus.Trying) && order.messageSent + .equals(MessageSent.NoneSent)) { + String requestId = messagingService.receiveRequest(1); + order.messageSent = MessageSent.PaymentTrying; + LOG.info("Order " + order.id + ": Payment Error message sent successfully," + + " request Id: " + requestId); + } + return; }; - Retry.HandleErrorIssue handleError = (o,err) -> { + Retry.HandleErrorIssue handleError = (o, err) -> { try { - if (o.messageSent.equals(MessageSent.NoneSent) && order.paid.equals(PaymentStatus.Trying) + if (o.messageSent.equals(MessageSent.NoneSent) && order.paid + .equals(PaymentStatus.Trying) && System.currentTimeMillis() - o.createdTime < messageTime) { - QueueTask qt = new QueueTask(order,TaskType.Messaging,1); + QueueTask qt = new QueueTask(order, TaskType.Messaging, 1); updateQueue(qt); LOG.warn("Order " + order.id + ": Error in sending Payment Error message, " + "trying to queue task and add to employee handle.."); employeeHandleIssue(o); - } + } } catch (InterruptedException e1) { e1.printStackTrace(); - } - return; + } + return; }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -516,28 +534,31 @@ public class Commander { public void run() { Retry.Operation op = (l) -> { if (!l.isEmpty()) { - LOG.warn("Order " + order.id + ": Error in connecting to employee handle, trying again.."); - throw l.remove(0); - } + LOG.warn("Order " + order.id + ": Error in connecting to employee handle," + + " trying again.."); + throw l.remove(0); + } if (!order.addedToEmployeeHandle) { - employeeDb.receiveRequest(order); + employeeDb.receiveRequest(order); order.addedToEmployeeHandle = true; LOG.info("Order " + order.id + ": Added order to employee database"); } - return; + return; }; - Retry.HandleErrorIssue handleError = (o,err) -> { + Retry.HandleErrorIssue handleError = (o, err) -> { try { - if (!o.addedToEmployeeHandle && System.currentTimeMillis() - order.createdTime < employeeTime) { - QueueTask qt = new QueueTask(order, TaskType.EmployeeDb,-1); + if (!o.addedToEmployeeHandle && System + .currentTimeMillis() - order.createdTime < employeeTime) { + QueueTask qt = new QueueTask(order, TaskType.EmployeeDb, -1); updateQueue(qt); - LOG.warn("Order " + order.id + ": Error in adding to employee db, trying to queue task.."); + LOG.warn("Order " + order.id + ": Error in adding to employee db," + + " trying to queue task.."); return; - } + } } catch (InterruptedException e1) { e1.printStackTrace(); } - return; + return; }; Retry r = new Retry(op, handleError, numOfRetries, retryDuration, e -> DatabaseUnavailableException.class.isAssignableFrom(e.getClass())); @@ -558,7 +579,7 @@ public class Commander { LOG.trace("Order " + qt.order.id + ": Started doing task of type " + qt.getType()); if (qt.firstAttemptTime == -1) { qt.firstAttemptTime = System.currentTimeMillis(); - } + } if (System.currentTimeMillis() - qt.firstAttemptTime >= queueTaskTime) { tryDequeue(); LOG.trace("Order " + qt.order.id + ": This queue task of type " + qt.getType() @@ -573,14 +594,15 @@ public class Commander { LOG.debug("Order " + qt.order.id + ": Trying to connect to payment service.."); } } else if (qt.taskType.equals(TaskType.Messaging)) { - if (qt.order.messageSent.equals(MessageSent.PaymentFail) + if (qt.order.messageSent.equals(MessageSent.PaymentFail) || qt.order.messageSent.equals(MessageSent.PaymentSuccessful)) { tryDequeue(); LOG.trace("Order " + qt.order.id + ": This messaging task already done, dequeue.."); } else if (qt.messageType == 1 && (!qt.order.messageSent.equals(MessageSent.NoneSent) || !qt.order.paid.equals(PaymentStatus.Trying))) { tryDequeue(); - LOG.trace("Order " + qt.order.id + ": This messaging task does not need to be done, dequeue.."); + LOG.trace("Order " + qt.order.id + ": This messaging task does not need to be done," + + " dequeue.."); } else if (qt.messageType == 0) { sendPaymentFailureMessage(qt.order); LOG.debug("Order " + qt.order.id + ": Trying to connect to messaging service.."); @@ -594,7 +616,8 @@ public class Commander { } else if (qt.taskType.equals(TaskType.EmployeeDb)) { if (qt.order.addedToEmployeeHandle) { tryDequeue(); - LOG.trace("Order " + qt.order.id + ": This employee handle task already done, dequeue.."); + LOG.trace("Order " + qt.order.id + ": This employee handle task already done," + + " dequeue.."); } else { employeeHandleIssue(qt.order); LOG.debug("Order " + qt.order.id + ": Trying to connect to employee handle.."); diff --git a/commander/src/main/java/com/iluwatar/commander/Database.java b/commander/src/main/java/com/iluwatar/commander/Database.java index 3f850f90a..ebd333e02 100644 --- a/commander/src/main/java/com/iluwatar/commander/Database.java +++ b/commander/src/main/java/com/iluwatar/commander/Database.java @@ -26,12 +26,14 @@ package com.iluwatar.commander; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; /** - * Database abstract class is extended by all databases in our example. The add and get - * methods are used by the respective service to add to database or get from database. + * Database abstract class is extended by all databases in our example. The add and get methods are + * used by the respective service to add to database or get from database. + * * @param T is the type of object being held by database. */ public abstract class Database { public abstract T add(T obj) throws DatabaseUnavailableException; - public abstract T get(String tId) throws DatabaseUnavailableException; + + public abstract T get(String id) throws DatabaseUnavailableException; } diff --git a/commander/src/main/java/com/iluwatar/commander/Order.java b/commander/src/main/java/com/iluwatar/commander/Order.java index 20002e1b9..0293c478c 100644 --- a/commander/src/main/java/com/iluwatar/commander/Order.java +++ b/commander/src/main/java/com/iluwatar/commander/Order.java @@ -34,11 +34,15 @@ public class Order { //can store all transactions ids also enum PaymentStatus { NotDone, Trying, Done - }; - + } + + ; + enum MessageSent { NoneSent, PaymentFail, PaymentTrying, PaymentSuccessful - }; + } + + ; final User user; final String item; @@ -78,5 +82,5 @@ public class Order { //can store all transactions ids also } return random.toString(); } - + } diff --git a/commander/src/main/java/com/iluwatar/commander/Retry.java b/commander/src/main/java/com/iluwatar/commander/Retry.java index 7b9d06d2d..65c92d3ef 100644 --- a/commander/src/main/java/com/iluwatar/commander/Retry.java +++ b/commander/src/main/java/com/iluwatar/commander/Retry.java @@ -30,29 +30,31 @@ import java.util.concurrent.atomic.AtomicInteger; import java.util.function.Predicate; /** - * Retry pattern + * Retry pattern. + * * @param is the type of object passed into HandleErrorIssue as a parameter. */ public class Retry { - /** - * Operation Interface will define method to be implemented. - */ + /** + * Operation Interface will define method to be implemented. + */ public interface Operation { - void operation(ArrayList list) throws Exception; + void operation(ArrayList list) throws Exception; } - /** - * HandleErrorIssue defines how to handle errors. - * @param is the type of object to be passed into the method as parameter. - */ - + /** + * HandleErrorIssue defines how to handle errors. + * + * @param is the type of object to be passed into the method as parameter. + */ + public interface HandleErrorIssue { void handleIssue(T obj, Exception e); } - + private static final Random RANDOM = new Random(); private final Operation op; @@ -64,7 +66,7 @@ public class Retry { private final ArrayList errors; Retry(Operation op, HandleErrorIssue handleError, int maxAttempts, - long maxDelay, Predicate... ignoreTests) { + long maxDelay, Predicate... ignoreTests) { this.op = op; this.handleError = handleError; this.maxAttempts = maxAttempts; @@ -76,10 +78,11 @@ public class Retry { /** * Performing the operation with retries. + * * @param list is the exception list - * @param obj is the parameter to be passed into handleIsuue method + * @param obj is the parameter to be passed into handleIsuue method */ - + public void perform(ArrayList list, T obj) throws Exception { do { try { @@ -92,15 +95,15 @@ public class Retry { return; //return here...dont go further } try { - long testDelay = (long) Math.pow(2, this.attempts.intValue()) * 1000 + RANDOM.nextInt(1000); + long testDelay = + (long) Math.pow(2, this.attempts.intValue()) * 1000 + RANDOM.nextInt(1000); long delay = testDelay < this.maxDelay ? testDelay : maxDelay; Thread.sleep(delay); } catch (InterruptedException f) { //ignore } } - } - while (true); + } while (true); } } diff --git a/commander/src/main/java/com/iluwatar/commander/Service.java b/commander/src/main/java/com/iluwatar/commander/Service.java index 64af79053..ddcc2d5bf 100644 --- a/commander/src/main/java/com/iluwatar/commander/Service.java +++ b/commander/src/main/java/com/iluwatar/commander/Service.java @@ -23,35 +23,37 @@ package com.iluwatar.commander; -import java.util.*; - import com.iluwatar.commander.exceptions.DatabaseUnavailableException; +import java.util.ArrayList; +import java.util.Hashtable; +import java.util.List; +import java.util.Random; /** - * Service class is an abstract class extended by all services in this example. They - * all have a public receiveRequest method to receive requests, which could also contain - * details of the user other than the implementation details (though we are not doing - * that here) and updateDb method which adds to their respective databases. There is a - * method to generate transaction/request id for the transactions/requests, which are - * then sent back. These could be stored by the {@link Commander} class in a separate - * database for reference (though we are not doing that here). + * Service class is an abstract class extended by all services in this example. They all have a + * public receiveRequest method to receive requests, which could also contain details of the user + * other than the implementation details (though we are not doing that here) and updateDb method + * which adds to their respective databases. There is a method to generate transaction/request id + * for the transactions/requests, which are then sent back. These could be stored by the {@link + * Commander} class in a separate database for reference (though we are not doing that here). */ public abstract class Service { - + protected final Database database; public ArrayList exceptionsList; private static final Random RANDOM = new Random(); private static final String ALL_CHARS = "ABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890"; private static final Hashtable USED_IDS = new Hashtable<>(); - protected Service(Database db, Exception...exc) { + protected Service(Database db, Exception... exc) { this.database = db; this.exceptionsList = new ArrayList<>(List.of(exc)); } - public abstract String receiveRequest(Object...parameters) throws DatabaseUnavailableException; - protected abstract String updateDb(Object...parameters) throws DatabaseUnavailableException; + public abstract String receiveRequest(Object... parameters) throws DatabaseUnavailableException; + + protected abstract String updateDb(Object... parameters) throws DatabaseUnavailableException; protected String generateId() { StringBuilder random = new StringBuilder(); diff --git a/commander/src/main/java/com/iluwatar/commander/employeehandle/EmployeeDatabase.java b/commander/src/main/java/com/iluwatar/commander/employeehandle/EmployeeDatabase.java index 0626e5ce0..3f5b7bcc0 100644 --- a/commander/src/main/java/com/iluwatar/commander/employeehandle/EmployeeDatabase.java +++ b/commander/src/main/java/com/iluwatar/commander/employeehandle/EmployeeDatabase.java @@ -23,10 +23,10 @@ package com.iluwatar.commander.employeehandle; -import java.util.Hashtable; import com.iluwatar.commander.Database; import com.iluwatar.commander.Order; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; +import java.util.Hashtable; /** * The Employee Database is where orders which have encountered some issue(s) are added. @@ -41,11 +41,11 @@ public class EmployeeDatabase extends Database { @Override public Order add(Order o) throws DatabaseUnavailableException { - return data.put(o.id,o); + return data.put(o.id, o); } @Override - public Order get(String oId) throws DatabaseUnavailableException { - return data.get(oId); + public Order get(String orderId) throws DatabaseUnavailableException { + return data.get(orderId); } } diff --git a/commander/src/main/java/com/iluwatar/commander/employeehandle/EmployeeHandle.java b/commander/src/main/java/com/iluwatar/commander/employeehandle/EmployeeHandle.java index ed3e36d7c..9f4d8fb48 100644 --- a/commander/src/main/java/com/iluwatar/commander/employeehandle/EmployeeHandle.java +++ b/commander/src/main/java/com/iluwatar/commander/employeehandle/EmployeeHandle.java @@ -28,21 +28,21 @@ import com.iluwatar.commander.Service; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; /** - * The EmployeeHandle class is the middle-man between {@link Commander} and - * {@link EmployeeDatabase}. + * The EmployeeHandle class is the middle-man between {@link Commander} and {@link + * EmployeeDatabase}. */ public class EmployeeHandle extends Service { - public EmployeeHandle(EmployeeDatabase db, Exception...exc) { + public EmployeeHandle(EmployeeDatabase db, Exception... exc) { super(db, exc); } - public String receiveRequest(Object...parameters) throws DatabaseUnavailableException { - return updateDb((Order)parameters[0]); + public String receiveRequest(Object... parameters) throws DatabaseUnavailableException { + return updateDb((Order) parameters[0]); } - protected String updateDb(Object...parameters) throws DatabaseUnavailableException { + protected String updateDb(Object... parameters) throws DatabaseUnavailableException { Order o = (Order) parameters[0]; if (database.get(o.id) == null) { database.add(o); diff --git a/commander/src/main/java/com/iluwatar/commander/exceptions/DatabaseUnavailableException.java b/commander/src/main/java/com/iluwatar/commander/exceptions/DatabaseUnavailableException.java index 71254fb31..8997b1a10 100644 --- a/commander/src/main/java/com/iluwatar/commander/exceptions/DatabaseUnavailableException.java +++ b/commander/src/main/java/com/iluwatar/commander/exceptions/DatabaseUnavailableException.java @@ -24,8 +24,8 @@ package com.iluwatar.commander.exceptions; /** - * DatabaseUnavailableException is thrown when database is unavailable and nothing - * can be added or retrieved. + * DatabaseUnavailableException is thrown when database is unavailable and nothing can be added or + * retrieved. */ public class DatabaseUnavailableException extends Exception { diff --git a/commander/src/main/java/com/iluwatar/commander/exceptions/PaymentDetailsErrorException.java b/commander/src/main/java/com/iluwatar/commander/exceptions/PaymentDetailsErrorException.java index 306cf4c18..eb7c0fb3f 100644 --- a/commander/src/main/java/com/iluwatar/commander/exceptions/PaymentDetailsErrorException.java +++ b/commander/src/main/java/com/iluwatar/commander/exceptions/PaymentDetailsErrorException.java @@ -24,8 +24,8 @@ package com.iluwatar.commander.exceptions; /** - * PaymentDetailsErrorException is thrown when the details entered are incorrect or - * payment cannot be made with the details given. + * PaymentDetailsErrorException is thrown when the details entered are incorrect or payment cannot + * be made with the details given. */ public class PaymentDetailsErrorException extends Exception { diff --git a/commander/src/main/java/com/iluwatar/commander/exceptions/ShippingNotPossibleException.java b/commander/src/main/java/com/iluwatar/commander/exceptions/ShippingNotPossibleException.java index 8c2b53341..b374f2a7d 100644 --- a/commander/src/main/java/com/iluwatar/commander/exceptions/ShippingNotPossibleException.java +++ b/commander/src/main/java/com/iluwatar/commander/exceptions/ShippingNotPossibleException.java @@ -24,8 +24,8 @@ package com.iluwatar.commander.exceptions; /** - * ShippingNotPossibleException is thrown when the address entered cannot be shipped to - * by service currently for some reason. + * ShippingNotPossibleException is thrown when the address entered cannot be shipped to by service + * currently for some reason. */ public class ShippingNotPossibleException extends Exception { diff --git a/commander/src/main/java/com/iluwatar/commander/messagingservice/MessagingDatabase.java b/commander/src/main/java/com/iluwatar/commander/messagingservice/MessagingDatabase.java index 7078726be..45bd1e23a 100644 --- a/commander/src/main/java/com/iluwatar/commander/messagingservice/MessagingDatabase.java +++ b/commander/src/main/java/com/iluwatar/commander/messagingservice/MessagingDatabase.java @@ -23,10 +23,10 @@ package com.iluwatar.commander.messagingservice; -import java.util.Hashtable; import com.iluwatar.commander.Database; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; import com.iluwatar.commander.messagingservice.MessagingService.MessageRequest; +import java.util.Hashtable; /** * The MessagingDatabase is where the MessageRequest is added. @@ -45,8 +45,8 @@ public class MessagingDatabase extends Database { } @Override - public MessageRequest get(String rId) throws DatabaseUnavailableException { - return data.get(rId); + public MessageRequest get(String requestId) throws DatabaseUnavailableException { + return data.get(requestId); } } diff --git a/commander/src/main/java/com/iluwatar/commander/messagingservice/MessagingService.java b/commander/src/main/java/com/iluwatar/commander/messagingservice/MessagingService.java index 2742dfd5d..1dcdac926 100644 --- a/commander/src/main/java/com/iluwatar/commander/messagingservice/MessagingService.java +++ b/commander/src/main/java/com/iluwatar/commander/messagingservice/MessagingService.java @@ -29,9 +29,9 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** - * The MessagingService is used to send messages to user regarding their order and - * payment status. In case an error is encountered in payment and this service is - * found to be unavailable, the order is added to the {@link EmployeeDatabase}. + * The MessagingService is used to send messages to user regarding their order and payment status. + * In case an error is encountered in payment and this service is found to be unavailable, the order + * is added to the {@link EmployeeDatabase}. */ public class MessagingService extends Service { @@ -39,7 +39,9 @@ public class MessagingService extends Service { enum MessageToSend { PaymentFail, PaymentTrying, PaymentSuccessful - }; + } + + ; class MessageRequest { String reqId; @@ -51,17 +53,16 @@ public class MessagingService extends Service { } } - public MessagingService(MessagingDatabase db, Exception...exc) { + public MessagingService(MessagingDatabase db, Exception... exc) { super(db, exc); } /** * Public method which will receive request from {@link Commander}. */ - - public String receiveRequest(Object...parameters) throws DatabaseUnavailableException { + public String receiveRequest(Object... parameters) throws DatabaseUnavailableException { int messageToSend = (int) parameters[0]; - String rId = generateId(); + String id = generateId(); MessageToSend msg = null; if (messageToSend == 0) { msg = MessageToSend.PaymentFail; @@ -70,11 +71,11 @@ public class MessagingService extends Service { } else { //messageToSend == 2 msg = MessageToSend.PaymentSuccessful; } - MessageRequest req = new MessageRequest(rId, msg); + MessageRequest req = new MessageRequest(id, msg); return updateDb(req); } - protected String updateDb(Object...parameters) throws DatabaseUnavailableException { + protected String updateDb(Object... parameters) throws DatabaseUnavailableException { MessageRequest req = (MessageRequest) parameters[0]; if (this.database.get(req.reqId) == null) { //idempotence, in case db fails here database.add(req); //if successful: @@ -86,13 +87,17 @@ public class MessagingService extends Service { String sendMessage(MessageToSend m) { if (m.equals(MessageToSend.PaymentSuccessful)) { - return "Msg: Your order has been placed and paid for successfully! Thank you for shopping with us!"; + return "Msg: Your order has been placed and paid for successfully!" + + " Thank you for shopping with us!"; } else if (m.equals(MessageToSend.PaymentTrying)) { - return "Msg: There was an error in your payment process, we are working on it and will return back to you" - + " shortly. Meanwhile, your order has been placed and will be shipped."; + return "Msg: There was an error in your payment process," + + " we are working on it and will return back to you shortly." + + " Meanwhile, your order has been placed and will be shipped."; } else { - return "Msg: There was an error in your payment process. Your order is placed and has been converted to COD." - + " Please reach us on CUSTOMER-CARE-NUBER in case of any queries. Thank you for shopping with us!"; + return "Msg: There was an error in your payment process." + + " Your order is placed and has been converted to COD." + + " Please reach us on CUSTOMER-CARE-NUBER in case of any queries." + + " Thank you for shopping with us!"; } } } diff --git a/commander/src/main/java/com/iluwatar/commander/paymentservice/PaymentDatabase.java b/commander/src/main/java/com/iluwatar/commander/paymentservice/PaymentDatabase.java index b597abe68..ed308dbfb 100644 --- a/commander/src/main/java/com/iluwatar/commander/paymentservice/PaymentDatabase.java +++ b/commander/src/main/java/com/iluwatar/commander/paymentservice/PaymentDatabase.java @@ -23,11 +23,10 @@ package com.iluwatar.commander.paymentservice; -import java.util.Hashtable; - import com.iluwatar.commander.Database; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; import com.iluwatar.commander.paymentservice.PaymentService.PaymentRequest; +import java.util.Hashtable; /** * PaymentDatabase is where the PaymentRequest is added, along with details. @@ -48,8 +47,8 @@ public class PaymentDatabase extends Database { } @Override - public PaymentRequest get(String tId) throws DatabaseUnavailableException { - return data.get(tId); + public PaymentRequest get(String requestId) throws DatabaseUnavailableException { + return data.get(requestId); } } diff --git a/commander/src/main/java/com/iluwatar/commander/paymentservice/PaymentService.java b/commander/src/main/java/com/iluwatar/commander/paymentservice/PaymentService.java index 9abb15db2..95ca92a65 100644 --- a/commander/src/main/java/com/iluwatar/commander/paymentservice/PaymentService.java +++ b/commander/src/main/java/com/iluwatar/commander/paymentservice/PaymentService.java @@ -27,8 +27,8 @@ import com.iluwatar.commander.Service; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; /** - * The PaymentService class receives request from the {@link Commander} and adds - * to the {@link PaymentDatabase}. + * The PaymentService class receives request from the {@link Commander} and adds to the {@link + * PaymentDatabase}. */ public class PaymentService extends Service { @@ -45,22 +45,22 @@ public class PaymentService extends Service { } } - public PaymentService(PaymentDatabase db, Exception...exc) { + public PaymentService(PaymentDatabase db, Exception... exc) { super(db, exc); } /** * Public method which will receive request from {@link Commander}. */ - - public String receiveRequest(Object...parameters) throws DatabaseUnavailableException { + + public String receiveRequest(Object... parameters) throws DatabaseUnavailableException { //it could also be sending a userid, payment details here or something, not added here - String tId = generateId(); - PaymentRequest req = new PaymentRequest(tId, (float)parameters[0]); + String id = generateId(); + PaymentRequest req = new PaymentRequest(id, (float) parameters[0]); return updateDb(req); } - protected String updateDb(Object...parameters) throws DatabaseUnavailableException { + protected String updateDb(Object... parameters) throws DatabaseUnavailableException { PaymentRequest req = (PaymentRequest) parameters[0]; if (database.get(req.transactionId) == null || !req.paid) { database.add(req); diff --git a/commander/src/main/java/com/iluwatar/commander/queue/Queue.java b/commander/src/main/java/com/iluwatar/commander/queue/Queue.java index 16fdaa883..1770e6c05 100644 --- a/commander/src/main/java/com/iluwatar/commander/queue/Queue.java +++ b/commander/src/main/java/com/iluwatar/commander/queue/Queue.java @@ -27,6 +27,7 @@ import com.iluwatar.commander.exceptions.IsEmptyException; /** * Queue data structure implementation. + * * @param is the type of object the queue will hold. */ @@ -47,15 +48,14 @@ public class Queue { } /** - * Queue constructor + * Queue constructor. */ - Queue() { front = null; rear = null; size = 0; } - + boolean isEmpty() { if (size == 0) { return true; @@ -63,7 +63,7 @@ public class Queue { return false; } } - + void enqueue(T obj) { if (front == null) { front = new Node(obj, null); @@ -75,7 +75,7 @@ public class Queue { } size++; } - + T dequeue() throws IsEmptyException { if (isEmpty()) { throw new IsEmptyException(); @@ -86,12 +86,12 @@ public class Queue { return (T) temp.value; } } - + T peek() throws IsEmptyException { if (isEmpty()) { throw new IsEmptyException(); } else { - return (T)front.value; + return (T) front.value; } } } diff --git a/commander/src/main/java/com/iluwatar/commander/queue/QueueDatabase.java b/commander/src/main/java/com/iluwatar/commander/queue/QueueDatabase.java index 6b9007b9f..3874cc27d 100644 --- a/commander/src/main/java/com/iluwatar/commander/queue/QueueDatabase.java +++ b/commander/src/main/java/com/iluwatar/commander/queue/QueueDatabase.java @@ -26,7 +26,6 @@ package com.iluwatar.commander.queue; import com.iluwatar.commander.Database; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; import com.iluwatar.commander.exceptions.IsEmptyException; - import java.util.ArrayList; import java.util.List; @@ -39,7 +38,7 @@ public class QueueDatabase extends Database { private Queue data; public ArrayList exceptionsList; - public QueueDatabase(Exception...exc) { + public QueueDatabase(Exception... exc) { this.data = new Queue<>(); this.exceptionsList = new ArrayList<>(List.of(exc)); } @@ -52,31 +51,33 @@ public class QueueDatabase extends Database { } /** - * peek method returns object at front without removing it from queue + * peek method returns object at front without removing it from queue. + * * @return object at front of queue - * @throws IsEmptyException if queue is empty + * @throws IsEmptyException if queue is empty * @throws DatabaseUnavailableException if queue db is unavailable */ - + public QueueTask peek() throws IsEmptyException, DatabaseUnavailableException { QueueTask qt = this.data.peek(); return qt; } /** - * dequeue method removes the object at front and returns it + * dequeue method removes the object at front and returns it. + * * @return object at front of queue - * @throws IsEmptyException if queue is empty + * @throws IsEmptyException if queue is empty * @throws DatabaseUnavailableException if queue db is unavailable */ - + public QueueTask dequeue() throws IsEmptyException, DatabaseUnavailableException { QueueTask qt = this.data.dequeue(); return qt; } @Override - public QueueTask get(String tId) throws DatabaseUnavailableException { + public QueueTask get(String taskId) throws DatabaseUnavailableException { return null; } diff --git a/commander/src/main/java/com/iluwatar/commander/queue/QueueTask.java b/commander/src/main/java/com/iluwatar/commander/queue/QueueTask.java index 206b2daf1..f8ba09fc1 100644 --- a/commander/src/main/java/com/iluwatar/commander/queue/QueueTask.java +++ b/commander/src/main/java/com/iluwatar/commander/queue/QueueTask.java @@ -31,13 +31,15 @@ import com.iluwatar.commander.Order; public class QueueTask { -/** - * TaskType is the type of task to be done. - */ + /** + * TaskType is the type of task to be done. + */ public enum TaskType { Messaging, Payment, EmployeeDb - }; + } + + ; public Order order; public TaskType taskType; @@ -46,26 +48,28 @@ public class QueueTask { but keeping it simple here*/ public long firstAttemptTime; //when first time attempt made to do task -/** - * QueueTask constructor - * @param o is the order for which the queuetask is being created - * @param t is the type of task to be done - * @param messageType if it is a message, which type of message - this could have instead been object varargs, - * and contained all additional details related to tasktype. - */ - + /** + * QueueTask constructor. + * + * @param o is the order for which the queuetask is being created + * @param t is the type of task to be done + * @param messageType if it is a message, which type of message - this could have instead been + * object varargs, and contained all additional details related to tasktype. + */ + public QueueTask(Order o, TaskType t, int messageType) { this.order = o; this.taskType = t; this.messageType = messageType; this.firstAttemptTime = -1; } - + /** - * getType method + * getType method. + * * @return String representing type of task */ - + public String getType() { if (!this.taskType.equals(TaskType.Messaging)) { return this.taskType.toString(); diff --git a/commander/src/main/java/com/iluwatar/commander/shippingservice/ShippingDatabase.java b/commander/src/main/java/com/iluwatar/commander/shippingservice/ShippingDatabase.java index fd2bf7996..a45dd00e1 100644 --- a/commander/src/main/java/com/iluwatar/commander/shippingservice/ShippingDatabase.java +++ b/commander/src/main/java/com/iluwatar/commander/shippingservice/ShippingDatabase.java @@ -23,17 +23,17 @@ package com.iluwatar.commander.shippingservice; -import java.util.Hashtable; import com.iluwatar.commander.Database; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; import com.iluwatar.commander.shippingservice.ShippingService.ShippingRequest; +import java.util.Hashtable; /** * ShippingDatabase is where the ShippingRequest objects are added. */ public class ShippingDatabase extends Database { - + private Hashtable data; public ShippingDatabase() { @@ -45,8 +45,8 @@ public class ShippingDatabase extends Database { return data.put(r.transactionId, r); } - public ShippingRequest get(String transactionId) throws DatabaseUnavailableException { - return data.get(transactionId); + public ShippingRequest get(String trasnactionId) throws DatabaseUnavailableException { + return data.get(trasnactionId); } } diff --git a/commander/src/main/java/com/iluwatar/commander/shippingservice/ShippingService.java b/commander/src/main/java/com/iluwatar/commander/shippingservice/ShippingService.java index a14690306..6539316b1 100644 --- a/commander/src/main/java/com/iluwatar/commander/shippingservice/ShippingService.java +++ b/commander/src/main/java/com/iluwatar/commander/shippingservice/ShippingService.java @@ -27,8 +27,8 @@ import com.iluwatar.commander.Service; import com.iluwatar.commander.exceptions.DatabaseUnavailableException; /** - * ShippingService class receives request from {@link Commander} class and adds it - * to the {@link ShippingDatabase}. + * ShippingService class receives request from {@link Commander} class and adds it to the {@link + * ShippingDatabase}. */ public class ShippingService extends Service { @@ -45,21 +45,22 @@ public class ShippingService extends Service { } } - public ShippingService(ShippingDatabase db, Exception...exc) { + public ShippingService(ShippingDatabase db, Exception... exc) { super(db, exc); } /** * Public method which will receive request from {@link Commander}. */ - - public String receiveRequest(Object...parameters) throws DatabaseUnavailableException { - String tId = generateId(); - ShippingRequest req = new ShippingRequest(tId, (String) parameters[0] /*item*/, (String) parameters[1]/*address*/); + + public String receiveRequest(Object... parameters) throws DatabaseUnavailableException { + String id = generateId(); + ShippingRequest req = + new ShippingRequest(id, (String) parameters[0] /*item*/, (String) parameters[1]/*address*/); return updateDb(req); } - protected String updateDb(Object...parameters) throws DatabaseUnavailableException { + protected String updateDb(Object... parameters) throws DatabaseUnavailableException { ShippingRequest req = (ShippingRequest) parameters[0]; if (this.database.get(req.transactionId) == null) { database.add(req);