Exercise 1: Adding a Second Business Rule and Watching the Gap Widen — Possible Solution ==================================================================== THE NEW RULE, ADDED INSIDE OrderService.get_order_total() ------------------------------ def get_order_total(self, order_id, is_loyalty_member): raw_total = self.repository.get(order_id) if is_loyalty_member: raw_total = raw_total * 0.9 if raw_total > 50: raw_total -= 5 # a second business rule, applied after the loyalty discount return raw_total A NOTE ON WHY A DISCOUNT WAS USED HERE, NOT A FEE ------------------------------ A first attempt at this exercise using a flat $5 SHIPPING FEE instead of a second discount was tried and found to be the wrong choice - adding a positive fee to the correct total actually made it CLOSER to the broken total (95 vs 100, a gap of only 5, smaller than the original gap of 10), because the fee pushes the correct total upward while the broken total stays fixed at the raw, undiscounted number. A second DISCOUNT (which only ever subtracts) is the rule that actually widens the gap, since it pushes the correct total further away from the broken total's fixed value. VERIFYING THE CORRECT PRESENTATION FUNCTION ------------------------------ correct: Your total: $85.00 manual: (100*0.9)-5 = 85.0 Matches exactly - the loyalty discount (100 -> 90) followed by the new $5-off-over-$50 rule (90 -> 85). VERIFYING THE BROKEN FUNCTION IS NOW WRONG BY MORE ------------------------------ broken: Your total: $100.00 gap now: 15.0 (was 10 before this exercise) display_order_total_broken() still reads the raw, undiscounted value straight from the repository - it was already missing the original 10% discount (a gap of 10), and now it's also missing the new $5-off rule, widening the gap to 15. WHY THIS CONFIRMS THIS CHAPTER'S OWN FINDING ------------------------------ Every new business rule added to OrderService widens the gap between the correct and broken presentation functions further, because the broken function's own error (reading raw data, applying zero business rules) doesn't grow on its own - it just falls further behind as OrderService accumulates more logic it never gets to run. WHY THIS WORKS AS AN ANSWER ------------------------------ The new rule is added directly inside the existing get_order_total() method following this chapter's own established shape, both totals are verified against hand calculations, and the growing gap is measured directly rather than only asserted - including an honest account of why the first, fee-based version of this rule would NOT have actually widened the gap, and why a second discount was the correct choice instead.