References
Достоинства
- Простое внедрение, работа с SQLAlchemy.
- Автоматическая генерация кода миграций на основе ORM-моделей.
- Возможность использования Python внутри кода с миграциями.
- Фиксация миграций в отдельной таблице
alembic_version
.
Недостатки
- Не фиксирует изменения имён таблиц и имён колонок (проверить в актуальной версии!)
Использование
Инициализация
Инициализация – создаст директорию ./alembic/
и файл ./alembic.ini
:
alembic init -t async alembic
Как настроить с SQLModel – см. на TestDriven.
Далее, в файле alembic.ini
необходимо указать корректное подключение к БД в параметре sqlalchemy.url
. Для Postgres используем postgres://
, без asyncpg
. Там же прописать prepend_sys_path = ..
, чтобы при запуске кода ниже нашелся модуль app
. (Это не надо делать, если выполнять команду ниже из папки, где лежит alembic.ini
).
В файле ./alembic/env.py
, там где # for 'autogenerate' support
, прописать что-то типа:
from app import Base
target_metadata = Base.metadata
Также в env.py
нужно корректно устанавливать строку для соединения с БД, исходя из настроек приложения. Что-то вроде:
config.set_main_option("sqlalchemy.url", f"{settings.DATABASE_URL}?async_fallback=True")
Делаем первую миграцию. Для создания миграции, должно быть возможно соединение с БД, указанной в настройках!
alembic revision --message="Init migration" --autogenerate
В директории ./alembic/versions/
появится .py
-файл миграции.
Применение миграций
Чтобы применить созданную миграцию, нужно выполнить:
alembic upgrade head
Идентификатор последней примененной миграции будет в БД в таблице alembic_version
.
Откат миграций
Чтобы откатиться, используем команду:
alembic downgrade <current_revision_id>-1
Отменить ВСЕ миграции, очистив БД:
alembic downgrade base
Очистить БД PostgreSQL поленостью “руками”:
DROP SCHEMA public CASCADE;
CREATE SCHEMA public;
Слияние миграций
Если есть несколько “параллельных” миграций (например, от разных разработчиков при совместной разработке), их необходимо объединить командой:
alembic merge heads -m "Merge migrations ... ... ..."
Создастся ещё одна миграция для слияния параллельных веток. После этого, можно применить команду alembic upgrade head
.
Добавляем NON-NULL поле в заполненную таблицу
Используем следующий трюк в миграции:
from typing import Sequence, Union
import sqlalchemy as sa
import sqlmodel
from alembic import op
# revision identifiers, used by Alembic.
revision: str = "fc274cf576c2"
down_revision: Union[str, None] = "cbd0bc20cc4c"
branch_labels: Union[str, Sequence[str], None] = None
depends_on: Union[str, Sequence[str], None] = None
def upgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.add_column(
"profiles",
sa.Column[[(]]
"platform",
sqlmodel.sql.sqltypes.AutoString(),
nullable=True,
),
)
#
# Временно делаем поле nullable, заполняем его чем-то, и потом
# возвращаем nullable=False выше. После применения этой миграции,
# удалить две следующие строки.
#
op.execute("UPDATE profiles SET platform = 'telegram'")
op.alter_column("profiles", "platform", nullable=False)
# ### end Alembic commands ###
def downgrade() -> None:
# ### commands auto generated by Alembic - please adjust! ###
op.drop_column("profiles", "platform")
# ### end Alembic commands ###
История миграций
Выводит историю применения всех миграций.
alembic history
Передача параметров при запуске миграции
При запуске Alembic передаём параметр param
со значением value
:
alembic -x param=value upgrade heads
Получаем это значение в env.py
:
param = context.get_x_argument(as_dictionary=True).get("param")
🔗 Миграции БД | Tooling
📂 Tooling | Последнее изменение: 29.01.2025 16:45