CWE, OWASP, криптография, аутентификация, авторизация
Безопасность — это не фича. Одна уязвимость может уничтожить компанию. Code review — последняя линия обороны.
# ❌ Уязвимо: нет проверки прав
@app.route('/api/users/<int:user_id>')
def get_user(user_id):
user = User.query.get(user_id)
return jsonify(user.to_dict()) # Любой может смотреть чужие данные!
# ✅ Безопасно: проверка прав
from flask_login import current_user
@app.route('/api/users/<int:user_id>')
def get_user(user_id):
if current_user.id != user_id and not current_user.is_admin:
abort(403, "Access denied")
user = User.query.get(user_id)
return jsonify(user.to_dict())Что проверять:
# ❌ Уязвимо: слабое хэширование
import hashlib
password_hash = hashlib.md5(password.encode()).hexdigest() # Взламывается за секунды
# ✅ Безопасно: bcrypt/argon2
from werkzeug.security import generate_password_hash, check_password_hash
password_hash = generate_password_hash(password) # bcrypt по умолчанию
# Проверка
check_password_hash(password_hash, password)Что проверять:
# ❌ SQL Injection
query = f"SELECT * FROM users WHERE id = {user_id}"
cursor.execute(query)
# ✅ Параметризованный запрос
cursor.execute("SELECT * FROM users WHERE id = %s", (user_id,))
# ❌ Command Injection
import os
os.system(f"ping {user_input}") # Выполнит любой код!
# ✅ Безопасно
import subprocess
subprocess.run(["ping", "-c", "1", user_input], check=True)# ❌ Уязвимо: нет expiration
import jwt
token = jwt.encode({"user_id": 123}, SECRET_KEY, algorithm="HS256")
# ✅ Безопасно: короткий lifetime + refresh
token = jwt.encode({
"user_id": 123,
"exp": datetime.utcnow() + timedelta(minutes=15), # Access token
"iat": datetime.utcnow()
}, SECRET_KEY, algorithm="HS256")
refresh_token = jwt.encode({
"user_id": 123,
"exp": datetime.utcnow() + timedelta(days=30), # Refresh token
"type": "refresh"
}, REFRESH_SECRET_KEY, algorithm="HS256")Что проверять:
# ❌ Уязвимо: сессия не регенерируется
@app.route('/login', methods=['POST'])
def login():
if authenticate(request.form):
session['user_id'] = user.id # Старая сессия!
return redirect('/dashboard')
# ✅ Безопасно: регенерация
@app.route('/login', methods=['POST'])
def login():
if authenticate(request.form):
session.clear() # Очистить старую
session.regenerate() # Новый ID
session['user_id'] = user.id
return redirect('/dashboard')# ❌ Уязвимо: самописное шифрование
def encrypt(data):
return bytes([b ^ 0x42 for b in data]) # XOR шифр — не криптография!
# ✅ Безопасно: проверенные библиотеки
from cryptography.fernet import Fernet
key = Fernet.generate_key()
cipher = Fernet(key)
encrypted = cipher.encrypt(data.encode())
decrypted = cipher.decrypt(encrypted).decode()# ❌ Уязвимо: не криптографически стойкий random
import random
token = random.randint(100000, 999999) # Предсказуемо!
# ✅ Безопасно: secrets
import secrets
token = secrets.token_urlsafe(32) # Криптографически стойкийКлючевая мысль: Безопасность требует глубины защиты. Проверяйте аутентификацию, авторизацию, инъекции, криптографию в каждом PR.
Вопросы ещё не добавлены
Вопросы для этой подтемы ещё не добавлены.