Lab 6 - TDD Application Service - Expose Kitchen Business Interface and Implement Transactions

1. Summary

In DDD, we use an Application Service to expose operations involving Aggregates and Repositories, or multiple Aggregates. An Application Service is the first immediate client of the core Domain Model.

We would eventually use the interface of an Application Service to expose its operations as a REST API or message-driven collaboration using RabbitMQ or Kafka.

In this lab, we’ll build out the ApplicationService for the Kitchen context.

We will complete 10 stories:

  1. The ability to find a KitchenOrder by its OnlineOrderRef.

  2. When an OnlineOrderPaidEvent is published by the Ordering context, create a KitchenOrder.

  3. The ability to start prep on a KitchenOrder.

  4. When a KitchenOrderPrepStartedEvent is published, create a Pizza for every KitchenOrder.Pizza, and then start prep on each Pizza.

  5. The ability to finish prep on a Pizza.

  6. When a PizzaPrepFinishedEvent is published, start baking the pizza.

  7. When a PizzaBakeStartedEvent is published, start baking the order.

  8. The ability to remove a pizza from the oven.

  9. When the first pizza in an order has finished baking (i.e. PizzaBakeFinishedEvent), start assembling the order.

  10. When the final pizza in an order has finished baking, finish assembling the order.

You can run com.mattstine.dddworkshop.pizzashop.suites.Lab6Suite to check your progress in this lab.

2. Instructions

  1. Implement the following command methods:

    • startOrderPrep()

    • finishPizzaPrep()

    • removePizzaFromOven()

  2. Implement the following finders:

    • findKitchenOrderByRef()

    • findKitchenOrderByOnlineOrderRef()

    • findPizzaByRef()

    • findPizzasByKitchenOrderRef()

  3. Subscribe to the ordering topic. On an OnlineOrderPaidEvent, retrieve the asssociated OnlineOrder by its Ref. Convert the OnlineOrder to a KitchenOrder, and add it to the repository.

  4. Subscribe to the ktichen_orders topic. On a KitchenOrderPrepStartedEvent, create a Pizza for each KitchenOrder.Pizza, and add it to the repository. Then startPrep() on the Pizza.

  5. Subscribe to the pizzas topic:

    • On a PizzaPrepFinishedEvent, retrieve the associated Pizza and startBake().

    • On a PizzaBakeStartedEvent, retrieve the associated KitchenOrder. If the KitchenOrder is prepping, startBake().

    • On a PizzaBakeFinishedEvent, retrieve the associated KitchenOrder. If the KitchenOrder is baking, startAssembly(). Next, retrieve all of the associated Pizza instances. If all of them have finished baking, finishAssembly on the KitchenOrder.