From 63225a3559cb688a5e2bab57f75c0bb92ddf40d9 Mon Sep 17 00:00:00 2001 From: jlightner Date: Tue, 31 Mar 2026 02:45:54 +0000 Subject: [PATCH] =?UTF-8?q?fix:=20migration=20008=20=E2=80=94=20use=20text?= =?UTF-8?q?=20column=20conversion=20to=20avoid=20PG=20enum=20transaction?= =?UTF-8?q?=20restriction?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../versions/008_rename_processing_status.py | 54 ++++++++++++++++--- 1 file changed, 47 insertions(+), 7 deletions(-) diff --git a/alembic/versions/008_rename_processing_status.py b/alembic/versions/008_rename_processing_status.py index f7f9ddd..a685ffe 100644 --- a/alembic/versions/008_rename_processing_status.py +++ b/alembic/versions/008_rename_processing_status.py @@ -3,10 +3,13 @@ Old: pending, transcribed, extracted, published New: not_started, queued, processing, error, complete +Uses text column conversion to avoid PG enum ADD VALUE transaction restriction. + Revision ID: 008_rename_processing_status Revises: 007_drop_review_columns """ from alembic import op +import sqlalchemy as sa revision = "008_rename_processing_status" down_revision = "007_drop_review_columns" @@ -15,21 +18,58 @@ depends_on = None def upgrade() -> None: - # Add new enum values first - op.execute("ALTER TYPE processing_status ADD VALUE IF NOT EXISTS 'not_started'") - op.execute("ALTER TYPE processing_status ADD VALUE IF NOT EXISTS 'queued'") - op.execute("ALTER TYPE processing_status ADD VALUE IF NOT EXISTS 'processing'") - op.execute("ALTER TYPE processing_status ADD VALUE IF NOT EXISTS 'error'") - op.execute("ALTER TYPE processing_status ADD VALUE IF NOT EXISTS 'complete'") - # Migrate existing rows + # 1. Convert column to text to break free of the old enum + op.alter_column( + "source_videos", "processing_status", + type_=sa.Text(), + existing_type=sa.Enum(name="processing_status"), + postgresql_using="processing_status::text", + ) + + # 2. Drop old enum type + op.execute("DROP TYPE IF EXISTS processing_status") + + # 3. Rename values in the text column op.execute("UPDATE source_videos SET processing_status = 'not_started' WHERE processing_status = 'pending'") op.execute("UPDATE source_videos SET processing_status = 'queued' WHERE processing_status = 'transcribed'") op.execute("UPDATE source_videos SET processing_status = 'processing' WHERE processing_status = 'extracted'") op.execute("UPDATE source_videos SET processing_status = 'complete' WHERE processing_status = 'published'") + # 4. Create new enum type + processing_status = sa.Enum( + "not_started", "queued", "processing", "error", "complete", + name="processing_status", + ) + processing_status.create(op.get_bind(), checkfirst=True) + + # 5. Convert column back to enum + op.alter_column( + "source_videos", "processing_status", + type_=processing_status, + existing_type=sa.Text(), + postgresql_using="processing_status::processing_status", + server_default="not_started", + ) + def downgrade() -> None: + op.alter_column( + "source_videos", "processing_status", + type_=sa.Text(), + existing_type=sa.Enum(name="processing_status"), + postgresql_using="processing_status::text", + ) + op.execute("DROP TYPE IF EXISTS processing_status") op.execute("UPDATE source_videos SET processing_status = 'pending' WHERE processing_status = 'not_started'") op.execute("UPDATE source_videos SET processing_status = 'transcribed' WHERE processing_status = 'queued'") op.execute("UPDATE source_videos SET processing_status = 'extracted' WHERE processing_status = 'processing'") op.execute("UPDATE source_videos SET processing_status = 'published' WHERE processing_status = 'complete'") + old_enum = sa.Enum("pending", "transcribed", "extracted", "published", name="processing_status") + old_enum.create(op.get_bind(), checkfirst=True) + op.alter_column( + "source_videos", "processing_status", + type_=old_enum, + existing_type=sa.Text(), + postgresql_using="processing_status::processing_status", + server_default="pending", + )