Security Testing
This document outlines security testing practices and procedures for the tracker REST API system.
Overview
Security testing is a critical component of the development lifecycle, ensuring that the application is protected against common vulnerabilities and attack vectors.
Authentication & Authorization Testing
JWT Token Security
Token Validation Tests
def test_jwt_token_validation():
"""Test JWT token validation with various scenarios"""
# Valid token test
valid_token = create_access_token(user_id=1)
assert validate_token(valid_token) is not None
# Expired token test
expired_token = create_expired_token(user_id=1)
with pytest.raises(TokenExpiredError):
validate_token(expired_token)
# Invalid signature test
invalid_token = "invalid.jwt.token"
with pytest.raises(InvalidTokenError):
validate_token(invalid_token)
Token Refresh Security
def test_refresh_token_security():
"""Test refresh token security mechanisms"""
# Test refresh token rotation
refresh_token = create_refresh_token(user_id=1)
new_tokens = refresh_access_token(refresh_token)
# Old refresh token should be invalidated
with pytest.raises(InvalidTokenError):
refresh_access_token(refresh_token)
Role-Based Access Control (RBAC)
def test_admin_only_endpoints():
"""Test that admin-only endpoints reject non-admin users"""
user_token = create_access_token(user_id=1, role="user")
admin_token = create_access_token(user_id=2, role="admin")
# User should be denied access
response = client.get("/api/v1/admin/users", headers={"Authorization": f"Bearer {user_token}"})
assert response.status_code == 403
# Admin should have access
response = client.get("/api/v1/admin/users", headers={"Authorization": f"Bearer {admin_token}"})
assert response.status_code == 200
Input Validation & Sanitization
SQL Injection Prevention
def test_sql_injection_prevention():
"""Test that SQL injection attempts are prevented"""
malicious_input = "'; DROP TABLE users; --"
response = client.get(f"/api/v1/users?search={malicious_input}")
assert response.status_code in [200, 400] # Should not cause server error
# Verify database integrity
users_count = db.query(User).count()
assert users_count > 0 # Table should still exist
XSS Prevention
def test_xss_prevention():
"""Test that XSS attempts are sanitized"""
xss_payload = "<script>alert('xss')</script>"
response = client.post("/api/v1/trackers", json={
"name": xss_payload,
"description": "Test tracker"
})
if response.status_code == 201:
tracker = response.json()
assert "<script>" not in tracker["name"]
assert "<script>" in tracker["name"] # Should be escaped
API Security Testing
Rate Limiting
def test_rate_limiting():
"""Test API rate limiting functionality"""
# Make multiple requests rapidly
responses = []
for _ in range(100):
response = client.get("/api/v1/trackers")
responses.append(response.status_code)
# Should eventually hit rate limit
assert 429 in responses # Too Many Requests
CORS Security
def test_cors_security():
"""Test CORS configuration security"""
# Test allowed origin
response = client.options("/api/v1/trackers", headers={
"Origin": "https://tracker-admin.glimpse.technology",
"Access-Control-Request-Method": "GET"
})
assert response.status_code == 200
assert "Access-Control-Allow-Origin" in response.headers
# Test disallowed origin
response = client.options("/api/v1/trackers", headers={
"Origin": "https://malicious-site.com",
"Access-Control-Request-Method": "GET"
})
assert "Access-Control-Allow-Origin" not in response.headers
Data Protection Testing
Sensitive Data Exposure
def test_password_not_exposed():
"""Test that passwords are never exposed in API responses"""
response = client.get("/api/v1/users/1")
user_data = response.json()
assert "password" not in user_data
assert "password_hash" not in user_data
Data Encryption
def test_sensitive_data_encryption():
"""Test that sensitive data is encrypted at rest"""
user = create_test_user(password="plaintext_password")
# Password should be hashed, not stored in plaintext
assert user.password_hash != "plaintext_password"
assert len(user.password_hash) > 50 # Bcrypt hash length
assert user.password_hash.startswith("$2b$") # Bcrypt prefix
Infrastructure Security Testing
Database Security
def test_database_connection_security():
"""Test database connection security"""
# Test that database connections use SSL in production
if settings.ENVIRONMENT == "production":
assert "sslmode=require" in settings.SQLALCHEMY_DATABASE_URI
Redis/Dragonfly Security
def test_redis_authentication():
"""Test Redis/Dragonfly authentication"""
# Test that Redis requires authentication
if settings.REDIS_PASSWORD:
# Should fail without password
with pytest.raises(ConnectionError):
redis_client = Redis(host=settings.REDIS_HOST, port=settings.REDIS_PORT)
redis_client.ping()
# Should succeed with password
authenticated_client = Redis(
host=settings.REDIS_HOST,
port=settings.REDIS_PORT,
password=settings.REDIS_PASSWORD
)
assert authenticated_client.ping() is True
Security Headers Testing
def test_security_headers():
"""Test that proper security headers are set"""
response = client.get("/api/v1/health")
# Check for security headers
assert "X-Content-Type-Options" in response.headers
assert response.headers["X-Content-Type-Options"] == "nosniff"
assert "X-Frame-Options" in response.headers
assert response.headers["X-Frame-Options"] == "DENY"
assert "X-XSS-Protection" in response.headers
assert response.headers["X-XSS-Protection"] == "1; mode=block"
Vulnerability Scanning
Automated Security Scanning
# Run security vulnerability scan
bandit -r app/ -f json -o security-report.json
# Check for known vulnerabilities in dependencies
safety check --json --output vulnerability-report.json
# OWASP ZAP automated scan
zap-baseline.py -t http://localhost:8000 -J zap-report.json
Manual Security Testing
Authentication Bypass Attempts
- Token Manipulation
- Modify JWT payload
- Change user ID in token
-
Use tokens from different users
-
Session Management
- Test session fixation
- Test concurrent sessions
- Test session timeout
Authorization Testing
- Horizontal Privilege Escalation
- Access other users' data
-
Modify other users' resources
-
Vertical Privilege Escalation
- Access admin functions as regular user
- Bypass role restrictions
Security Test Automation
CI/CD Integration
# .github/workflows/security.yml
name: Security Tests
on: [push, pull_request]
jobs:
security:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Run Bandit Security Scan
run: |
pip install bandit
bandit -r app/ -f json -o bandit-report.json
- name: Run Safety Check
run: |
pip install safety
safety check --json --output safety-report.json
- name: Upload Security Reports
uses: actions/upload-artifact@v2
with:
name: security-reports
path: |
bandit-report.json
safety-report.json
Security Testing Checklist
Pre-deployment Security Tests
- Authentication mechanisms tested
- Authorization controls verified
- Input validation confirmed
- SQL injection prevention tested
- XSS prevention verified
- CSRF protection enabled
- Rate limiting functional
- Security headers present
- Sensitive data protection verified
- Error handling secure (no information leakage)
Production Security Monitoring
- Security logging enabled
- Intrusion detection configured
- Vulnerability scanning scheduled
- Security incident response plan ready
- Regular security audits planned
Security Testing Tools
Static Analysis
- Bandit - Python security linter
- Safety - Dependency vulnerability scanner
- SonarQube - Code quality and security analysis
Dynamic Analysis
- OWASP ZAP - Web application security scanner
- Burp Suite - Web vulnerability scanner
- Postman - API security testing
Infrastructure Security
- Nmap - Network security scanner
- Docker Bench - Docker security best practices
- Trivy - Container vulnerability scanner
Reporting Security Issues
Internal Reporting
- Create security issue in internal tracker
- Mark as confidential/private
- Assign to security team
- Follow responsible disclosure timeline
External Reporting
- Contact security team via secure channel
- Provide detailed vulnerability description
- Include proof of concept (if safe)
- Allow reasonable time for fix before disclosure
This security testing framework ensures comprehensive coverage of potential vulnerabilities and maintains the security posture of the tracker REST API system.