12

Python3에서 Flask를 사용하여 웹 응용 프로그램을 개발합니다. db migrate/upgrade에서 postgresql 열거 형에 문제가 있습니다.sqlalchemy postgresql enum이 db 이주시 유형을 생성하지 않습니다.

나는 모델에 열 "상태"를 추가 :

class Banner(db.Model): 
    ... 
    status = db.Column(db.Enum('active', 'inactive', 'archive', name='banner_status')) 
    ... 
python manage.py db migrate에 의해

생성 마이그레이션은 다음과 같습니다

from alembic import op 
import sqlalchemy as sa 

def upgrade(): 
    op.add_column('banner', sa.Column('status', sa.Enum('active', 'inactive', 'archive', name='banner_status'), nullable=True)) 

def downgrade(): 
    op.drop_column('banner', 'status') 

내가 python manage.py db upgrade 할 때 오류 얻을 :

... 
sqlalchemy.exc.ProgrammingError: (psycopg2.ProgrammingError) type "banner_status" does not exist 
LINE 1: ALTER TABLE banner ADD COLUMN status banner_status 

[SQL: 'ALTER TABLE banner ADD COLUMN status banner_status'] 

마이그레이션이 "banner_status"유형을 생성하지 않는 이유 "?

내가 뭘 잘못하고 있니?

$ pip freeze 
alembic==0.8.6 
Flask==0.10.1 
Flask-Fixtures==0.3.3 
Flask-Login==0.3.2 
Flask-Migrate==1.8.0 
Flask-Script==2.0.5 
Flask-SQLAlchemy==2.1 
itsdangerous==0.24 
Jinja2==2.8 
Mako==1.0.4 
MarkupSafe==0.23 
psycopg2==2.6.1 
python-editor==1.0 
requests==2.10.0 
SQLAlchemy==1.0.13 
Werkzeug==0.11.9 
+1

읽기 자료 http://stackoverflow.com/questions/14845203/altering-an-enum-field-using-alembic 및 https://bitbucket.org/zzzeek/alembic/issues/67/autogenerate-with-enums -on-postgres-dont는 열거 형을 수동으로 생성하고 삭제해야 할 수도 있습니다. –

답변

25

나는이를 사용하여이 문제를 결정했습니다.

나는 마이그레이션 및 마이그레이션의 코드는 다음과 같이이다 변경 :

from alembic import op 
import sqlalchemy as sa 
from sqlalchemy.dialects import postgresql 

def upgrade(): 
    banner_status = postgresql.ENUM('active', 'inactive', 'archive', name='banner_status') 
    banner_status.create(op.get_bind()) 

    op.add_column('banner', sa.Column('status', sa.Enum('active', 'inactive', 'archive', name='banner_status'), nullable=True)) 

def downgrade(): 
    op.drop_column('banner', 'status') 

    banner_status = postgresql.ENUM('active', 'inactive', 'archive', name='banner_status') 
    banner_status.drop(op.get_bind()) 

을 그리고 지금 python manage.py db upgrade\downgrade이 성공적으로 실행됩니다.

+0

다운 그레이드의 경우 SQL을 직접 실행하여 중복을 피할 수 있습니다 (적어도 postgres의 경우) : op.execute ("DROP TYPE banner_status;") – Geekfish