Базы данных и Flask-SQLAlchemy: настройка
База данных хранит данные между запусками. ORM позволяет работать с ней через объекты Python, а не сырой SQL. Flask-SQLAlchemy связывает эту мощь с Flask.
ORM (объектно-реляционное отображение) превращает строки таблиц в объекты Python и наоборот. Ты пишешь user.name, а не SQL-запрос. Flask-SQLAlchemy 3.x даёт объект db, который сам настраивает движок и сессию под Flask.
Пока данные жили в памяти — они исчезали при перезапуске. Нужна постоянная память: база данных. Можно писать SQL руками, но это утомительно и опасно (инъекции, ручная сборка строк). ORM решает это: таблица становится классом, строка — объектом, столбец — атрибутом.
Flask-SQLAlchemy — официальная интеграция SQLAlchemy с Flask. В версии 3.x объект db создаётся на базе декларативного класса и подключается через фабрику:
# extensions.py
from flask_sqlalchemy import SQLAlchemy
from sqlalchemy.orm import DeclarativeBase
class Base(DeclarativeBase):
pass
db = SQLAlchemy(model_class=Base)
# __init__.py (фабрика)
from .extensions import db
def create_app():
app = Flask(__name__)
app.config["SQLALCHEMY_DATABASE_URI"] = "sqlite:///app.db"
db.init_app(app)
return app
Строка SQLALCHEMY_DATABASE_URI задаёт базу: sqlite:///app.db для разработки (файл на диске), postgresql://... для продакшена. SQLite не требует сервера — идеален для учёбы. db.init_app привязывает расширение к приложению (помнишь паттерн из урока про фабрику).
ORM избавляет не только от рутины написания SQL, но и от целого класса уязвимостей: при работе через объекты и параметризованные запросы SQL-инъекции практически исключены, тогда как ручная склейка строк запроса — классический источник взломов. Flask-SQLAlchemy 3.x берёт на себя настройку движка и сессии под жизненный цикл Flask, поэтому тебе не нужно вручную управлять соединениями. Выбор базы стоит делать осознанно: SQLite — файл без отдельного сервера, идеален для учёбы, прототипов и тестов; PostgreSQL — надёжная серверная СУБД для продакшена с конкурентным доступом. Строку подключения, как и секреты, держат в переменных окружения, чтобы разработка и продакшен использовали разные базы без правки кода.
Как работает под капотом
db управляет двумя вещами: движком (engine) — пулом соединений с базой — и сессией (session) — «рабочим столом», где копятся изменения до commit. ORM транслирует операции с объектами в SQL и обратно.
Python-объект User ORM-слой База данных
────────────────── ──────── ───────────
user.name = "Анна" ──▶ db.session ──▶ UPDATE users
db.session.commit() ──▶ собрать SQL ──▶ SET name='Анна'
выполнить через engine (пул)
User(...) ◀── собрать объект ◀── SELECT * FROM users
Смоделируем суть ORM: объект Python ↔ строка-словарь «таблицы».
table = [] # имитация таблицы users
class User:
def __init__(self, name, email):
self.name = name
self.email = email
def save(obj): # как db.session.add + commit
row = {"id": len(table) + 1, "name": obj.name, "email": obj.email}
table.append(row)
return row["id"]
def all_users(): # как select(User)
return [User(r["name"], r["email"]) for r in table]
save(User("Анна", "[email protected]"))
save(User("Боб", "[email protected]"))
for u in all_users():
print(u.name, u.email)
Запусти: объекты сохраняются как строки и читаются обратно объектами. Настоящий SQLAlchemy делает то же, но с реальной базой, типами столбцов и SQL под капотом.
Частые ошибки
- Создавать db внутри фабрики. Тогда модели не смогут его импортировать. Создавай в extensions.py, привязывай через init_app.
- Забыть SQLALCHEMY_DATABASE_URI. Без строки подключения база неизвестна.
- Тащить продакшен на SQLite под нагрузкой. SQLite хорош для учёбы; для боевого многопользовательского сервиса — PostgreSQL.
Best practices
- db — глобально в extensions.py, init_app — в фабрике.
- Строку подключения бери из переменной окружения, не хардкодь.
- SQLite для разработки/тестов, PostgreSQL для продакшена.
Что запомнить
- ORM отображает таблицы на классы, строки на объекты Python.
- Flask-SQLAlchemy 3.x даёт объект db с движком и сессией.
- db создают в extensions.py пустым, привязывают через init_app в фабрике.
- SQLite — для разработки, PostgreSQL — для продакшена; URI из окружения.
Итог: ORM связывает объекты Python и таблицы, Flask-SQLAlchemy 3.x даёт объект db с движком и сессией, подключаемый через init_app. Дальше — описание моделей-таблиц.