diff --git a/pom.xml b/pom.xml
index 8b21a31..e7e0e3a 100644
--- a/pom.xml
+++ b/pom.xml
@@ -29,8 +29,14 @@
assertj-core
3.18.0
+
+ org.hamcrest
+ hamcrest-all
+ 1.3
+
+
diff --git a/src/main/java/com/serenitydojo/fruitmarket/Catalog.java b/src/main/java/com/serenitydojo/fruitmarket/Catalog.java
index a1c19ec..de8df11 100644
--- a/src/main/java/com/serenitydojo/fruitmarket/Catalog.java
+++ b/src/main/java/com/serenitydojo/fruitmarket/Catalog.java
@@ -1,7 +1,9 @@
package com.serenitydojo.fruitmarket;
import java.util.HashMap;
+import java.util.List;
import java.util.Map;
+import java.util.stream.Collectors;
public class Catalog {
@@ -11,8 +13,19 @@ public PriceSetter setPriceOf(Fruit fruit) {
return new PriceSetter(this, fruit);
}
+ public List getAvailableFruit() {
+ return pricePerKilo.keySet()
+ .stream()
+ .map(Enum::name)
+ .sorted()
+ .collect(Collectors.toList());
+ }
+
public Double getPriceOf(Fruit fruit) {
- return pricePerKilo.get(fruit);
+ if (pricePerKilo.containsKey(fruit)) {
+ return pricePerKilo.get(fruit);
+ }
+ throw new FruitUnavailableException(fruit.name() + " currently unavailable");
}
public static class PriceSetter {
diff --git a/src/main/java/com/serenitydojo/fruitmarket/FruitUnavailableException.java b/src/main/java/com/serenitydojo/fruitmarket/FruitUnavailableException.java
new file mode 100644
index 0000000..bafd22e
--- /dev/null
+++ b/src/main/java/com/serenitydojo/fruitmarket/FruitUnavailableException.java
@@ -0,0 +1,9 @@
+package com.serenitydojo.fruitmarket;
+
+public class FruitUnavailableException extends RuntimeException {
+ public FruitUnavailableException(String message) {
+ super(message);
+ }
+
+
+}
diff --git a/src/main/java/com/serenitydojo/fruitmarket/ShoppingCart.java b/src/main/java/com/serenitydojo/fruitmarket/ShoppingCart.java
index 0eee991..ba22911 100644
--- a/src/main/java/com/serenitydojo/fruitmarket/ShoppingCart.java
+++ b/src/main/java/com/serenitydojo/fruitmarket/ShoppingCart.java
@@ -11,4 +11,36 @@ public ShoppingCart(Catalog catalog) {
this.catalog = catalog;
this.items = new ArrayList<>();
}
+
+ public ShoppingCartAdder add(Double amount) {
+ return new ShoppingCartAdder(this, amount);
+ }
+
+
+ public List getItems() {
+ return new ArrayList<>(items);
+ }
+
+ public Double getTotalPrice() {
+ return items.stream().mapToDouble(ShoppingCartItem::getTotalCost).sum();
+ }
+
+ public class ShoppingCartAdder {
+ private final ShoppingCart shoppingCart;
+ private final Double amount;
+
+ public ShoppingCartAdder(ShoppingCart shoppingCart, Double amount) {
+ this.shoppingCart = shoppingCart;
+ this.amount = amount;
+ }
+
+ public ShoppingCart kilosOf(Fruit fruit) {
+ double basePrice = shoppingCart.catalog.getPriceOf(fruit);
+ double discountedPrice = (amount >= 5) ? basePrice * 0.9 : basePrice;
+ ShoppingCartItem item = new ShoppingCartItem(fruit, amount, discountedPrice * amount);
+ shoppingCart.items.add(item);
+ return shoppingCart;
+ }
+ }
+
}
diff --git a/src/test/java/com/serenitydojo/fruitmarket/TheCatalog.java b/src/test/java/com/serenitydojo/fruitmarket/TheCatalog.java
index 23801da..e2aabd4 100644
--- a/src/test/java/com/serenitydojo/fruitmarket/TheCatalog.java
+++ b/src/test/java/com/serenitydojo/fruitmarket/TheCatalog.java
@@ -1,11 +1,22 @@
package com.serenitydojo.fruitmarket;
+import org.junit.Before;
import org.junit.Test;
import static com.serenitydojo.fruitmarket.Fruit.*;
import static org.assertj.core.api.Assertions.assertThat;
public class TheCatalog {
+ Catalog catalog;
+
+ @Before
+ public void createANewCatalog(){
+ catalog = new Catalog();
+ catalog.setPriceOf(Apple).to(4.00)
+ .setPriceOf(Orange).to(5.50)
+ .setPriceOf(Banana).to(4.50)
+ .setPriceOf(Pear).to(4.50);
+ }
@Test
public void shouldBeAbleToUpdateTheCurrentPriceOfAFruit() {
@@ -14,4 +25,56 @@ public void shouldBeAbleToUpdateTheCurrentPriceOfAFruit() {
catalog.setPriceOf(Apple).to(4.00);
assertThat(catalog.getPriceOf(Apple)).isEqualTo(4.00);
}
+
+ @Test
+ public void shouldListTheAvailableFruitInAlphabeticalOrder() {
+ assertThat(catalog.getAvailableFruit()).containsExactly("Apple", "Banana", "Orange", "Pear");
+
+ }
+
+ @Test
+ public void shouldReturnTheCorrectPricesOfEachFruitInSeason(){
+ assertThat(catalog.getPriceOf(Apple)).isEqualTo(4.00);
+ assertThat(catalog.getPriceOf(Orange)).isEqualTo(5.50);
+ }
+
+ @Test(expected = FruitUnavailableException.class)
+ public void shouldReportAnExceptionIfAFruitIsNotAvailable() {
+ catalog.getPriceOf(Strawberries);
+ }
+
+ //Test I added
+ @Test
+ public void shouldNotBeAbleToAddFruitWithWrongPrice(){
+ Catalog catalog = new Catalog();
+
+ catalog.setPriceOf(Banana).to(4.25);
+
+ assertThat(catalog.getPriceOf(Banana)).isNotEqualTo(4.50);
+ }
+
+ //Test I added
+ @Test
+ public void shouldListAllAvailableFruits(){
+ catalog = new Catalog();
+ catalog.setPriceOf(Apple).to(4.00)
+ .setPriceOf(Orange).to(5.50)
+ .setPriceOf(Banana).to(4.50)
+ .setPriceOf(Pear).to(4.50)
+ .setPriceOf(Peach).to(3.25)
+ .setPriceOf(Strawberries).to(4.25)
+ .setPriceOf(Mulberries).to(3.0);
+
+
+
+ assertThat(catalog.getAvailableFruit()).containsExactlyInAnyOrder("Apple", "Banana", "Pear","Orange","Mulberries","Peach", "Strawberries");
+
+
+
+
+
+
+
+ }
+
}
diff --git a/src/test/java/com/serenitydojo/fruitmarket/TheShoppingCart.java b/src/test/java/com/serenitydojo/fruitmarket/TheShoppingCart.java
new file mode 100644
index 0000000..c09dee4
--- /dev/null
+++ b/src/test/java/com/serenitydojo/fruitmarket/TheShoppingCart.java
@@ -0,0 +1,87 @@
+package com.serenitydojo.fruitmarket;
+
+import org.junit.Before;
+import org.junit.Test;
+
+import static com.serenitydojo.fruitmarket.Fruit.*;
+import static org.assertj.core.api.Assertions.assertThat;
+
+
+public class TheShoppingCart {
+
+ Catalog catalog;
+ ShoppingCart cart;
+
+ @Before
+ public void setupCatalog() {
+ catalog = new Catalog();
+ catalog.setPriceOf(Apple).to(4.00)
+ .setPriceOf(Orange).to(5.50)
+ .setPriceOf(Banana).to(4.50)
+ .setPriceOf(Pear).to(4.50);
+
+ cart = new ShoppingCart(catalog);
+ }
+
+ @Test
+ public void shouldStartWithNoItems() {
+ assertThat(cart.getItems()).isEmpty();
+ }
+
+ @Test
+ public void shouldKeepTrackOfItemsAddedToTheCart() {
+ cart.add(2.0).kilosOf(Apple)
+ .add(3.0).kilosOf(Orange);
+
+ assertThat(cart.getItems()).hasSize(2);
+ }
+
+ @Test
+ public void shouldUseTheCatalogToCalculateThePriceOfItemsAddedToTheCart() {
+ cart.add(2.0).kilosOf(Apple)
+ .add(2.0).kilosOf(Orange)
+ .add(1.0).kilosOf(Pear);
+
+ assertThat(cart.getTotalPrice()).isEqualTo(23.50);
+ }
+
+ @Test
+ public void shouldKeepTrackOfTheTotalPrice() {
+ cart.add(2.0).kilosOf(Apple);
+
+ ShoppingCartItem apples = cart.getItems().get(0);
+
+ assertThat(apples.getFruit()).isEqualTo(Apple);
+ assertThat(apples.getQuantity()).isEqualTo(2.0);
+ assertThat(apples.getTotalCost()).isEqualTo(8.00);
+ }
+
+ @Test
+ public void shouldGiveBulkDiscountsDiscount() {
+ cart.add(10.0).kilosOf(Apple);
+
+ assertThat(cart.getTotalPrice()).isEqualTo(36.00);
+ }
+
+ @Test
+ public void buildDiscountsOnlyApplyToQuantitiesOverFiveKgs() {
+ cart.add(10.0).kilosOf(Apple);
+ cart.add(2.00).kilosOf(Orange);
+
+ assertThat(cart.getTotalPrice()).isEqualTo(47.00);
+ }
+
+// Test I added
+ @Test
+ public void shouldNotAllowNegativeBalance(){
+ cart.add(10.0).kilosOf(Apple);
+ cart.add(2.00).kilosOf(Orange);
+
+ assertThat(cart.getTotalPrice()).isNotEqualTo(-51.0);
+
+ }
+
+
+
+
+}