Reserve Inventory Behind One Call

Step 1: Reserve Inventory Behind One Call

A caller placing an order should not have to know that three subsystems exist. That is the whole point of the Facade pattern: one method, place_order, sits in front of Inventory, Payment, and Shipping and coordinates them, so the outside world sees a single simple entry point.

The three subsystems are already written for you and injected into the facade. You never rewrite them, you only call them. Inventory.reserve(item, qty) returns True and decrements stock when there is enough on hand, and returns False otherwise.

Start small. In this step, place_order only talks to Inventory:

  • Try to reserve qty of item.
  • If the reservation fails, return the dict with ok set to False and reason set to out_of_stock.
  • If it succeeds, return the dict with ok set to True. The payment and shipping steps come later.
Hints
Starter code
class Inventory:
    def __init__(self, stock):
        self.stock = dict(stock)

    def reserve(self, item, qty):
        if self.stock.get(item, 0) >= qty:
            self.stock[item] -= qty
            return True
        return False

    def release(self, item, qty):
        self.stock[item] = self.stock.get(item, 0) + qty


class Payment:
    def __init__(self, balance):
        self.balance = balance

    def charge(self, amount):
        if amount <= self.balance:
            self.balance -= amount
            return True
        return False


class Shipping:
    def schedule(self, item):
        return "trk-" + item


class CheckoutFacade:
    def __init__(self, inventory, payment, shipping):
        self.inventory = inventory
        self.payment = payment
        self.shipping = shipping
        self.orders = []

    def place_order(self, item, qty, amount):
        """Reserve inventory, then confirm the order."""
        # TODO: reserve qty of item via self.inventory.reserve(item, qty).
        # If the reservation fails, return {"ok": False, "reason": "out_of_stock"}.
        # On a successful reservation, return {"ok": True} for now.
        pass
Write it on a laptop

The editor and the test runner need a wide screen. Open this page on a desktop browser and your progress will be waiting.