From bfc6cbf7d947d1aac02df02911a677da79178ab4 Mon Sep 17 00:00:00 2001 From: boris Date: Mon, 22 Sep 2025 19:55:39 +0100 Subject: [PATCH] Added alembic configuration --- .github/workflows/ci.yml | 2 +- alembic.ini | 39 ++++++++++++++++++++++++ alembic/env.py | 64 ++++++++++++++++++++++++++++++++++++++++ alembic/script.py.mako | 0 app/db/base.py | 5 +++- 5 files changed, 108 insertions(+), 2 deletions(-) create mode 100644 alembic.ini create mode 100644 alembic/env.py create mode 100644 alembic/script.py.mako diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 5fc7a53..5567419 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -43,7 +43,7 @@ jobs: needs: lint services: postgres: - image: postgres:16 + image: postgres:17-alpine env: POSTGRES_DB: keywarden POSTGRES_USER: postgres diff --git a/alembic.ini b/alembic.ini new file mode 100644 index 0000000..37160fd --- /dev/null +++ b/alembic.ini @@ -0,0 +1,39 @@ +[alembic] +# Path to migration scripts +script_location = alembic + +# Set to 'true' to auto-generate migrations with naming convention support +timezone = UTC + +[loggers] +keys = root,sqlalchemy,alembic + +[handlers] +keys = console + +[formatters] +keys = generic + +[logger_root] +level = WARN +handlers = console +qualname = + +[logger_sqlalchemy] +level = WARN +handlers = +qualname = sqlalchemy.engine + +[logger_alembic] +level = INFO +handlers = +qualname = alembic + +[handler_console] +class = StreamHandler +args = (sys.stderr,) +level = NOTSET +formatter = generic + +[formatter_generic] +format = %(levelname)-5.5s [%(name)s] %(message)s \ No newline at end of file diff --git a/alembic/env.py b/alembic/env.py new file mode 100644 index 0000000..43cef03 --- /dev/null +++ b/alembic/env.py @@ -0,0 +1,64 @@ +import asyncio +from logging.config import fileConfig + +from sqlalchemy import pool +from sqlalchemy.ext.asyncio import AsyncEngine, create_async_engine + +from alembic import context + +# Import your app's config & models +from app.core.config import settings +from app.db.base import Base # imports all models via app/models/__init__.py + +# Alembic Config object +config = context.config + +# Set up Python logging from alembic.ini +if config.config_file_name is not None: + fileConfig(config.config_file_name) + +# Target metadata (for autogenerate) +target_metadata = Base.metadata + +# DSN from your app config (e.g. postgresql+asyncpg://…) +DB_URL = settings.POSTGRES_DSN + + +def run_migrations_offline(): + """Run migrations in 'offline' mode.""" + url = DB_URL + context.configure( + url=url, + target_metadata=target_metadata, + literal_binds=True, + dialect_opts={"paramstyle": "named"}, + ) + + with context.begin_transaction(): + context.run_migrations() + + +def do_run_migrations(connection): + context.configure(connection=connection, target_metadata=target_metadata) + + with context.begin_transaction(): + context.run_migrations() + + +async def run_migrations_online(): + """Run migrations in 'online' mode with async engine.""" + connectable: AsyncEngine = create_async_engine( + DB_URL, + poolclass=pool.NullPool, + ) + + async with connectable.connect() as connection: + await connection.run_sync(do_run_migrations) + + await connectable.dispose() + + +if context.is_offline_mode(): + run_migrations_offline() +else: + asyncio.run(run_migrations_online()) \ No newline at end of file diff --git a/alembic/script.py.mako b/alembic/script.py.mako new file mode 100644 index 0000000..e69de29 diff --git a/app/db/base.py b/app/db/base.py index c6e45b1..72eb97b 100644 --- a/app/db/base.py +++ b/app/db/base.py @@ -2,4 +2,7 @@ from app.models.user import User from app.models.server import Server from app.models.sshkey import SSHKey from app.models.access_request import AccessRequest -from app.models.audit import AuditEvent \ No newline at end of file +from app.models.audit import AuditEvent + +from sqlalchemy.orm import declarative_base +Base = declarative_base() \ No newline at end of file