Files
Church-Music/legacy-site/backend/migrate_database.py

83 lines
3.4 KiB
Python

"""
Database migration script to add indexes and constraints to existing database.
Run this after updating the models to apply schema changes to production database.
"""
from postgresql_models import engine, Base
from sqlalchemy import text
def migrate_database():
print("Starting database migration...")
with engine.connect() as conn:
# Start transaction
trans = conn.begin()
try:
# Add indexes if they don't exist (PostgreSQL syntax)
indexes = [
"CREATE INDEX IF NOT EXISTS idx_profile_name ON profiles(name)",
"CREATE INDEX IF NOT EXISTS idx_song_title ON songs(title)",
"CREATE INDEX IF NOT EXISTS idx_song_artist ON songs(artist)",
"CREATE INDEX IF NOT EXISTS idx_song_band ON songs(band)",
"CREATE INDEX IF NOT EXISTS idx_plan_date ON plans(date)",
"CREATE INDEX IF NOT EXISTS idx_plan_profile ON plans(profile_id)",
"CREATE INDEX IF NOT EXISTS idx_plan_songs_plan ON plan_songs(plan_id)",
"CREATE INDEX IF NOT EXISTS idx_plan_songs_order ON plan_songs(plan_id, order_index)",
"CREATE INDEX IF NOT EXISTS idx_profile_songs_profile ON profile_songs(profile_id)",
"CREATE INDEX IF NOT EXISTS idx_profile_song_keys ON profile_song_keys(profile_id, song_id)"
]
for idx_sql in indexes:
print(f"Creating index: {idx_sql}")
conn.execute(text(idx_sql))
# Add unique constraints if they don't exist
constraints = [
("plan_songs", "uq_plan_song", "plan_id, song_id"),
("profile_songs", "uq_profile_song", "profile_id, song_id"),
("profile_song_keys", "uq_profile_song_key", "profile_id, song_id")
]
for table, constraint_name, columns in constraints:
try:
check_sql = text("""
SELECT 1 FROM pg_constraint
WHERE conname = :constraint_name
""")
result = conn.execute(check_sql, {"constraint_name": constraint_name}).fetchone()
if not result:
constraint_sql = f"ALTER TABLE {table} ADD CONSTRAINT {constraint_name} UNIQUE ({columns})"
print(f"Adding constraint: {constraint_sql}")
conn.execute(text(constraint_sql))
else:
print(f"Constraint {constraint_name} already exists, skipping")
except Exception as e:
print(f"Warning: Could not add constraint {constraint_name}: {e}")
trans.commit()
print("Migration completed successfully!")
except Exception as e:
trans.rollback()
print(f"Migration failed: {e}")
raise
if __name__ == "__main__":
import sys
print("="*60)
print("Database Migration Script")
print("="*60)
print("This will add indexes and constraints to your database.")
print("Make sure you have a backup before proceeding!")
print("="*60)
response = input("Continue? (yes/no): ")
if response.lower() == 'yes':
migrate_database()
else:
print("Migration cancelled.")
sys.exit(0)