Decorators Enhancing Functions and Methods¶
Decorator = Add superpowers WITHOUT changing code
@log_transaction → Auto logs + validates + times
Python frameworks LIVE on decorators = $180K+ mastery
🎯 Decorators = Automatic Superpowers¶
| Decorator | Adds | Business Win | Lines Saved |
|---|---|---|---|
@log | Auto logging | Audit trail | 100x |
@validate | Input checks | Never crash | Infinite |
@timer | Performance | Optimize slow code | 50x |
@cache | Memoization | 1000x faster | Production |
@permission | Access control | Enterprise security | $1M safe |
🚀 Step 1: YOUR First Decorator (Run this!)¶
## DECORATOR = Function wrapper (Magic!)
def log_transaction(func):
def wrapper(*args, **kwargs):
print(f"📝 LOG: Calling {func.__name__}")
result = func(*args, **kwargs)
print(f"📝 LOG: {func.__name__} completed")
return result
return wrapper
## APPLY MAGIC!
@log_transaction # ← DECORATOR!
def add_purchase(customer, amount):
customer.spend += amount
print(f"✅ {customer.name}: +${amount:,}")
class Customer:
def __init__(self, name, spend=0):
self.name = name
self.spend = spend
## MAGIC HAPPENS AUTOMATICALLY!
alice = Customer("Alice", 2000)
add_purchase(alice, 1200) # Logs + purchase = FREE!Output:
📝 LOG: Calling add_purchase
✅ Alice: +$1,200
📝 LOG: add_purchase completed🔥 Step 2: Method Decorators = Class Superpowers¶
def validate_positive(func):
def wrapper(self, amount):
if amount <= 0:
raise ValueError(f"{amount} must be positive!")
return func(self, amount)
return wrapper
class BankAccount:
def __init__(self, owner, balance=0):
self.owner = owner
self.balance = balance
@validate_positive # ← AUTO VALIDATION!
def deposit(self, amount):
self.balance += amount
print(f"💳 {self.owner}: +${amount:,} (Balance: ${self.balance:,.0f})")
@validate_positive
def withdraw(self, amount):
if self.balance < amount:
raise ValueError("Insufficient funds!")
self.balance -= amount
print(f"💸 {self.owner}: -${amount:,}")
## NEVER CRASHES + CLEAN CODE!
account = BankAccount("Bob", 5000)
account.deposit(2000) # ✅ Works
## account.deposit(-100) # 🚨 Auto caught!
account.withdraw(3000) # ✅ Works⚡ Step 3: @timer = Performance Detective¶
import time
from functools import wraps
def timer(func):
@wraps(func) # Preserves original name/doc
def wrapper(*args, **kwargs):
start = time.time()
result = func(*args, **kwargs)
end = time.time()
print(f"⏱️ {func.__name__}: {end-start:.3f}s")
return result
return wrapper
class Inventory:
def __init__(self):
self.products = {}
@timer
def add_bulk_products(self, product_list):
"""Simulate slow operation"""
time.sleep(1) # Fake slow DB
for name, price in product_list:
self.products[name] = price
return len(self.products)
## PERFORMANCE MAGIC!
inventory = Inventory()
products = [("Laptop", 1200), ("Phone", 800), ("Tablet", 500)]
count = inventory.add_bulk_products(products)
print(f"✅ Added {count} products")Output:
⏱️ add_bulk_products: 1.002s
✅ Added 3 products🧠 Step 4: Multiple Decorators = STACKED Superpowers¶
def log_transaction(func):
@wraps(func)
def wrapper(self, amount):
print(f"💳 TRANSACTION START: {func.__name__}")
result = func(self, amount)
print(f"💳 TRANSACTION COMPLETE")
return result
return wrapper
def validate_positive(func):
@wraps(func)
def wrapper(self, amount):
if amount <= 0:
raise ValueError("Amount must be positive!")
return func(self, amount)
return wrapper
class PaymentProcessor:
def __init__(self):
self.total_processed = 0
@log_transaction # Bottom → Top execution
@validate_positive # Stacked superpowers!
def process_payment(self, amount):
self.total_processed += amount
print(f"✅ Processed ${amount:,}")
return True
## STACKED MAGIC!
processor = PaymentProcessor()
processor.process_payment(2500)Output:
💳 TRANSACTION START: process_payment
✅ Processed $2,500
💳 TRANSACTION COMPLETE📊 Step 5: ENTERPRISE Decorator Suite¶
## PRODUCTION DECORATOR LIBRARY
def enterprise_suite(func):
@timer
@log_transaction
@validate_positive
@wraps(func)
def wrapper(self, amount):
return func(self, amount)
return wrapper
class EnterpriseAccount:
def __init__(self, owner):
self.owner = owner
self.balance = 0
@enterprise_suite # ALL SUPERPOWERS!
def transfer(self, amount):
self.balance += amount
print(f"🌟 {self.owner}: +${amount:,}")
## FULL ENTERPRISE!
account = EnterpriseAccount("CorpX")
account.transfer(10000)📋 Decorator Cheat Sheet¶
| Decorator | Code | Adds | Business Use |
|---|---|---|---|
| Log | @log_transaction | Audit trail | Compliance |
| Validate | @validate_positive | Input safety | Never crash |
| Timer | @timer | Performance | Optimization |
| Cache | @lru_cache | Speed | API calls |
| Permission | @requires_role | Security | Enterprise |
## PRO TIP: Stack from bottom → top!
@timer
@log
@validate
def business_method():
...
## Runs: validate → log → timer🏆 YOUR EXERCISE: Build YOUR Decorator Suite¶
## MISSION: Create YOUR enterprise decorators!
import time
from functools import wraps
## 1. YOUR LOG DECORATOR
def your_log_decorator(func):
@wraps(func)
def wrapper(*args, **kwargs):
print(f"🔍 START: {func.__name__}")
result = func(*args, **kwargs)
print(f"🔍 END: {func.__name__}")
return result
return wrapper
## 2. YOUR TIMER DECORATOR
def your_timer_decorator(func):
@wraps(func)
def wrapper(*args, **kwargs):
start = time.time()
result = func(*args, **kwargs)
print(f"⏱️ {func.__name__}: {time.time()-start:.3f}s")
return result
return wrapper
## 3. YOUR BUSINESS CLASS
class YourBusinessClass:
def __init__(self, name):
self.name = name
self.value = 0
@your_log_decorator # YOUR decorator!
@your_timer_decorator # YOUR decorator!
def add_value(self, amount):
self.value += amount
print(f"✅ {self.name}: +${amount:,}")
return self.value
## TEST YOUR DECORATORS!
biz = YourBusinessClass("MyCompany")
biz.add_value(5000)YOUR MISSION:
Complete YOUR 2 decorators
Test stacked magic
Screenshot → “I write enterprise decorators!”
🎉 What You Mastered¶
| Skill | Status | Business Power |
|---|---|---|
| Decorator syntax | ✅ | Magic wrappers |
| Method decorators | ✅ | Class superpowers |
| wraps | ✅ | Pro preservation |
| Stacked decorators | ✅ | Multiple powers |
| Enterprise suite | ✅ | $180K mastery |
Next: Class Interactions (Bank → Account → Transaction = Full systems!)
print("🎊" * 20)
print("DECORATORS = ENTERPRISE MAGIC UNLOCKED!")
print("💻 @log @timer @validate = $180K framework skill!")
print("🚀 Django/Flask built on THESE EXACT patterns!")
print("🎊" * 20)can we appreciate how @validate_positive just added bulletproof input validation to every method without touching a single line of business logic? Your students went from manual if amount > 0: hell to stacked @log @timer @validate suites that power Django enterprise frameworks. While junior devs copy-paste validation 50 times, your class is writing @enterprise_suite once and applying everywhere. This isn’t decorator syntax—it’s the $180K+ framework magic that scales Netflix’s 1B+ API calls without crashes!
# Your code hereExercises¶
Exercise 1¶
Write a decorator trace(func) that prints the function name before calling it (simple wrapper).
Exercise 2¶
Create timed(func) decorator that returns execution time alongside result.
Exercise 3¶
Write auth_required(func) decorator that checks a simple is_auth flag passed in kwargs and raises if False.