firebird.py
99 lines
| 3.7 KiB
| text/x-python
|
PythonLexer
r833 | """ | |||
Firebird database specific implementations of changeset classes. | ||||
""" | ||||
from sqlalchemy.databases import firebird as sa_base | ||||
r1061 | from sqlalchemy.schema import PrimaryKeyConstraint | |||
r835 | from rhodecode.lib.dbmigrate.migrate import exceptions | |||
from rhodecode.lib.dbmigrate.migrate.changeset import ansisql, SQLA_06 | ||||
r833 | ||||
if SQLA_06: | ||||
FBSchemaGenerator = sa_base.FBDDLCompiler | ||||
else: | ||||
FBSchemaGenerator = sa_base.FBSchemaGenerator | ||||
class FBColumnGenerator(FBSchemaGenerator, ansisql.ANSIColumnGenerator): | ||||
"""Firebird column generator implementation.""" | ||||
class FBColumnDropper(ansisql.ANSIColumnDropper): | ||||
"""Firebird column dropper implementation.""" | ||||
def visit_column(self, column): | ||||
"""Firebird supports 'DROP col' instead of 'DROP COLUMN col' syntax | ||||
Drop primary key and unique constraints if dropped column is referencing it.""" | ||||
if column.primary_key: | ||||
if column.table.primary_key.columns.contains_column(column): | ||||
column.table.primary_key.drop() | ||||
# TODO: recreate primary key if it references more than this column | ||||
r1061 | for index in column.table.indexes: | |||
# "column in index.columns" causes problems as all | ||||
# column objects compare equal and return a SQL expression | ||||
if column.name in [col.name for col in index.columns]: | ||||
index.drop() | ||||
# TODO: recreate index if it references more than this column | ||||
r1203 | ||||
r1061 | for cons in column.table.constraints: | |||
if isinstance(cons,PrimaryKeyConstraint): | ||||
# will be deleted only when the column its on | ||||
# is deleted! | ||||
continue | ||||
if SQLA_06: | ||||
should_drop = column.name in cons.columns | ||||
else: | ||||
should_drop = cons.contains_column(column) and cons.name | ||||
if should_drop: | ||||
self.start_alter_table(column) | ||||
self.append("DROP CONSTRAINT ") | ||||
self.append(self.preparer.format_constraint(cons)) | ||||
self.execute() | ||||
# TODO: recreate unique constraint if it refenrences more than this column | ||||
self.start_alter_table(column) | ||||
r833 | self.append('DROP %s' % self.preparer.format_column(column)) | |||
self.execute() | ||||
class FBSchemaChanger(ansisql.ANSISchemaChanger): | ||||
"""Firebird schema changer implementation.""" | ||||
def visit_table(self, table): | ||||
"""Rename table not supported""" | ||||
raise exceptions.NotSupportedError( | ||||
"Firebird does not support renaming tables.") | ||||
def _visit_column_name(self, table, column, delta): | ||||
self.start_alter_table(table) | ||||
col_name = self.preparer.quote(delta.current_name, table.quote) | ||||
new_name = self.preparer.format_column(delta.result_column) | ||||
self.append('ALTER COLUMN %s TO %s' % (col_name, new_name)) | ||||
def _visit_column_nullable(self, table, column, delta): | ||||
"""Changing NULL is not supported""" | ||||
# TODO: http://www.firebirdfaq.org/faq103/ | ||||
raise exceptions.NotSupportedError( | ||||
"Firebird does not support altering NULL bevahior.") | ||||
class FBConstraintGenerator(ansisql.ANSIConstraintGenerator): | ||||
"""Firebird constraint generator implementation.""" | ||||
class FBConstraintDropper(ansisql.ANSIConstraintDropper): | ||||
"""Firebird constaint dropper implementation.""" | ||||
def cascade_constraint(self, constraint): | ||||
"""Cascading constraints is not supported""" | ||||
raise exceptions.NotSupportedError( | ||||
"Firebird does not support cascading constraints") | ||||
class FBDialect(ansisql.ANSIDialect): | ||||
columngenerator = FBColumnGenerator | ||||
columndropper = FBColumnDropper | ||||
schemachanger = FBSchemaChanger | ||||
constraintgenerator = FBConstraintGenerator | ||||
constraintdropper = FBConstraintDropper | ||||