una tablas primary primaria llave foreign foranea eliminar drop definir declarar crear compuesta como clave agregar sqlalchemy alembic

sqlalchemy - tablas - Agregar clave principal a la tabla MySQL existente en alambique



eliminar primary key mysql (1)

Estoy tratando de agregar una columna de clave primaria ''id'' a una tabla MySQL ya existente utilizando alambique. Intenté lo siguiente ...

op.add_column(''mytable'', sa.Column(''id'', sa.Integer(), nullable=False)) op.alter_column(''mytable'', ''id'', autoincrement=True, existing_type=sa.Integer(), existing_server_default=False, existing_nullable=False)

pero obtuve el siguiente error

sqlalchemy.exc.OperationalError: (OperationalError) (1075, ''Incorrect table definition; there can be only one auto column and it must be defined as a key'') ''ALTER TABLE mytable CHANGE id id INTEGER NOT NULL AUTO_INCREMENT'' ()

parece que la instrucción sql generada por el alambique no agregó PRIMARY KEY al final de la declaración alter. ¿Podría haberme perdido algunas configuraciones?

¡Gracias por adelantado!


Pasé algún tiempo investigando el código fuente del alambique, y esto no parece ser compatible. Puede especificar claves principales al crear una tabla, pero no al agregar columnas. De hecho, verifica específicamente y no le permitirá:

# from alembic.operations.add_column, line 284 for constraint in t.constraints: if not isinstance(constraint, schema.PrimaryKeyConstraint): self.impl.add_constraint(constraint)

Miré a mi alrededor, y agregar una clave principal a una tabla existente puede dar como resultado un comportamiento no especificado: no se supone que las claves primarias sean nulas, por lo que su motor puede o no crear claves primarias para las filas existentes. Consulte esta discusión de SO para obtener más información: Insertar clave primaria de incremento automático en la tabla existente

Acababa de ejecutar la consulta alter directamente, y crear claves principales si es necesario.

op.execute("ALTER TABLE mytable ADD id INT PRIMARY KEY AUTO_INCREMENT;")

Si realmente necesita compatibilidad entre motores, el gran martillo sería (1) crear una nueva tabla idéntica a la anterior con una clave principal, (2) migrar todos sus datos, (3) eliminar la tabla anterior y (4) ) cambiar el nombre de la nueva tabla.

Espero que ayude.