Input Validation and Sanitization
Every piece of data that enters your application from the outside world is potentially dangerous. Users make mistakes, and attackers deliberately send malicious input. Input validation is your first line of defense.
Never Trust User Input
This principle is fundamental to secure coding. Even if your frontend validates input, your backend must validate it again. Why? Because anyone can bypass your frontend and send requests directly to your API.
Treat all incoming data as suspicious until proven otherwise.
Validation vs Sanitization
These terms are related but different:
Validation checks whether input is acceptable. Is it the right type? The right length? In the expected format? Invalid input gets rejected.
Sanitization transforms input to make it safe. Remove dangerous characters, escape HTML, encode special symbols. Sanitized input can be used safely.
You often need both: validate first, then sanitize what passes validation.
Common Validation Checks
For a todo application, validate:
def validate_todo(text):
if not isinstance(text, str):
raise ValueError("Text must be a string")
text = text.strip()
if not text:
raise ValueError("Text cannot be empty")
if len(text) > 500:
raise ValueError("Text cannot exceed 500 characters")
return text
Adjust the rules based on your application's needs. An email field needs different validation than a todo field.
Frontend vs Backend Validation
Frontend validation improves user experience. Users get immediate feedback without waiting for a server round-trip.
Backend validation provides actual security. It's the only validation that matters because attackers can bypass the frontend entirely.
Always validate on the backend. Frontend validation is a nice-to-have, not a security measure.
Protecting Against Common Attacks
SQL Injection: Never build SQL queries by concatenating strings. Use parameterized queries:
# Dangerous - never do this
cursor.execute(f"SELECT * FROM todos WHERE id = {user_input}")
# Safe - always do this
cursor.execute("SELECT * FROM todos WHERE id = ?", (user_input,))
Cross-Site Scripting (XSS): When displaying user input in HTML, escape it. In JavaScript, use textContent instead of innerHTML. Most template engines escape by default.
Using AI for Security Review
AI can spot validation gaps you might miss:
"Review this endpoint for security vulnerabilities and suggest input validation improvements."
Paste your code and let AI identify potential issues. It won't catch everything, but it's a helpful extra check.