Module 1 • 50 min read
Python for Backend Development
Learn Python fundamentals and build your first REST API with FastAPI.
What You'll Learn
- Python syntax, data types, and functions
- Object-oriented programming in Python
- Building REST APIs with FastAPI
- Database integration with SQLAlchemy
1. Python Basics
Python is a versatile, readable language perfect for backend development. Let's start with the fundamentals you'll use every day.
Variables and Data Types
# Variables (no type declaration needed)
name = "Alice"
age = 30
is_developer = True
salary = 75000.50
# Lists (mutable, ordered)
languages = ["Python", "JavaScript", "Go"]
languages.append("Rust")
# Dictionaries (key-value pairs)
user = {
"name": "Alice",
"email": "alice@example.com",
"role": "developer"
}
# Tuples (immutable)
coordinates = (10.5, 20.3)
# Sets (unique values)
tags = {"python", "backend", "api"}
# Type hints (recommended for clarity)
def greet(name: str) -> str:
return f"Hello, {name}!"
# List comprehensions (powerful and concise)
squares = [x**2 for x in range(10)]
even_numbers = [x for x in range(20) if x % 2 == 0]2. Functions and Classes
Functions and OOP
# Functions with default arguments
def create_user(name: str, role: str = "user", active: bool = True):
return {
"name": name,
"role": role,
"active": active
}
# *args and **kwargs
def log_event(event: str, *tags, **metadata):
print(f"Event: {event}")
print(f"Tags: {tags}")
print(f"Metadata: {metadata}")
log_event("user_login", "auth", "success", user_id=123, ip="192.168.1.1")
# Classes
class User:
def __init__(self, name: str, email: str):
self.name = name
self.email = email
self._password = None # Private attribute
def set_password(self, password: str):
# In real app, hash the password
self._password = password
def check_password(self, password: str) -> bool:
return self._password == password
def __str__(self):
return f"User({self.name}, {self.email})"
# Inheritance
class Admin(User):
def __init__(self, name: str, email: str, permissions: list):
super().__init__(name, email)
self.permissions = permissions
def has_permission(self, permission: str) -> bool:
return permission in self.permissions
# Usage
admin = Admin("Bob", "bob@example.com", ["read", "write", "delete"])
print(admin.has_permission("write")) # True3. Building a REST API with FastAPI
FastAPI is a modern, fast framework for building APIs. It includes automatic documentation, type validation, and async support out of the box.
Your First FastAPI Application
# main.py
from fastapi import FastAPI, HTTPException
from pydantic import BaseModel
from typing import List, Optional
app = FastAPI(title="User API", version="1.0.0")
# Pydantic models for request/response validation
class UserCreate(BaseModel):
name: str
email: str
age: Optional[int] = None
class User(BaseModel):
id: int
name: str
email: str
age: Optional[int] = None
# In-memory database (use real DB in production)
users_db: List[User] = []
next_id = 1
@app.get("/")
def read_root():
return {"message": "Welcome to User API"}
@app.post("/users", response_model=User, status_code=201)
def create_user(user: UserCreate):
global next_id
new_user = User(
id=next_id,
name=user.name,
email=user.email,
age=user.age
)
users_db.append(new_user)
next_id += 1
return new_user
@app.get("/users", response_model=List[User])
def get_users(skip: int = 0, limit: int = 10):
return users_db[skip:skip + limit]
@app.get("/users/{user_id}", response_model=User)
def get_user(user_id: int):
for user in users_db:
if user.id == user_id:
return user
raise HTTPException(status_code=404, detail="User not found")
@app.put("/users/{user_id}", response_model=User)
def update_user(user_id: int, user_update: UserCreate):
for i, user in enumerate(users_db):
if user.id == user_id:
updated_user = User(
id=user_id,
name=user_update.name,
email=user_update.email,
age=user_update.age
)
users_db[i] = updated_user
return updated_user
raise HTTPException(status_code=404, detail="User not found")
@app.delete("/users/{user_id}")
def delete_user(user_id: int):
for i, user in enumerate(users_db):
if user.id == user_id:
users_db.pop(i)
return {"message": "User deleted"}
raise HTTPException(status_code=404, detail="User not found")
# Run with: uvicorn main:app --reload
# Docs available at: http://localhost:8000/docs4. Database Integration
SQLAlchemy with FastAPI
# database.py
from sqlalchemy import create_engine, Column, Integer, String
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import sessionmaker
DATABASE_URL = "sqlite:///./users.db"
engine = create_engine(DATABASE_URL, connect_args={"check_same_thread": False})
SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=engine)
Base = declarative_base()
# models.py
class UserModel(Base):
__tablename__ = "users"
id = Column(Integer, primary_key=True, index=True)
name = Column(String, index=True)
email = Column(String, unique=True, index=True)
age = Column(Integer, nullable=True)
Base.metadata.create_all(bind=engine)
# main.py (updated)
from fastapi import Depends
from sqlalchemy.orm import Session
def get_db():
db = SessionLocal()
try:
yield db
finally:
db.close()
@app.post("/users", response_model=User)
def create_user(user: UserCreate, db: Session = Depends(get_db)):
db_user = UserModel(
name=user.name,
email=user.email,
age=user.age
)
db.add(db_user)
db.commit()
db.refresh(db_user)
return db_user
@app.get("/users", response_model=List[User])
def get_users(skip: int = 0, limit: int = 10, db: Session = Depends(get_db)):
users = db.query(UserModel).offset(skip).limit(limit).all()
return users5. Authentication & Security
JWT Authentication
from fastapi import Depends, HTTPException, status
from fastapi.security import OAuth2PasswordBearer, OAuth2PasswordRequestForm
from jose import JWTError, jwt
from passlib.context import CryptContext
from datetime import datetime, timedelta
SECRET_KEY = "your-secret-key-here"
ALGORITHM = "HS256"
ACCESS_TOKEN_EXPIRE_MINUTES = 30
pwd_context = CryptContext(schemes=["bcrypt"], deprecated="auto")
oauth2_scheme = OAuth2PasswordBearer(tokenUrl="token")
def verify_password(plain_password: str, hashed_password: str) -> bool:
return pwd_context.verify(plain_password, hashed_password)
def get_password_hash(password: str) -> str:
return pwd_context.hash(password)
def create_access_token(data: dict):
to_encode = data.copy()
expire = datetime.utcnow() + timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
to_encode.update({"exp": expire})
encoded_jwt = jwt.encode(to_encode, SECRET_KEY, algorithm=ALGORITHM)
return encoded_jwt
async def get_current_user(token: str = Depends(oauth2_scheme)):
credentials_exception = HTTPException(
status_code=status.HTTP_401_UNAUTHORIZED,
detail="Could not validate credentials",
headers={"WWW-Authenticate": "Bearer"},
)
try:
payload = jwt.decode(token, SECRET_KEY, algorithms=[ALGORITHM])
email: str = payload.get("sub")
if email is None:
raise credentials_exception
except JWTError:
raise credentials_exception
# Get user from database
user = get_user_by_email(email)
if user is None:
raise credentials_exception
return user
@app.post("/token")
async def login(form_data: OAuth2PasswordRequestForm = Depends()):
user = authenticate_user(form_data.username, form_data.password)
if not user:
raise HTTPException(
status_code=status.HTTP_401_UNAUTHORIZED,
detail="Incorrect username or password"
)
access_token = create_access_token(data={"sub": user.email})
return {"access_token": access_token, "token_type": "bearer"}
@app.get("/users/me")
async def read_users_me(current_user: User = Depends(get_current_user)):
return current_userKey Takeaways
- Python is readable and powerful for backend development
- FastAPI provides automatic validation and documentation
- Pydantic models ensure type safety and data validation
- SQLAlchemy is the standard ORM for database operations
- JWT tokens are the modern standard for API authentication
- Always hash passwords and use environment variables for secrets
Practice Exercises
Build These Projects
- 1. Blog API: Create a REST API for a blog with posts, comments, and tags.
- 2. Task Manager: Build a todo API with user authentication and task categories.
- 3. E-commerce Backend: Design an API for products, cart, and orders.
- 4. Real-time Chat: Implement WebSocket support for a chat application.