SchemaEditor

  • class BaseDatabaseSchemaEditor[源代码]
  • Django's migration system is split into two parts; the logic for calculatingand storing what operations should be run (django.db.migrations), and thedatabase abstraction layer that turns things like "create a model" or"delete a field" into SQL - which is the job of the SchemaEditor.

It's unlikely that you will want to interact directly with SchemaEditor asa normal developer using Django, but if you want to write your own migrationsystem, or have more advanced needs, it's a lot nicer than writing SQL.

Each database backend in Django supplies its own version of SchemaEditor,and it's always accessible via the connection.schema_editor() contextmanager:

  1. with connection.schema_editor() as schema_editor:
  2. schema_editor.delete_model(MyModel)

It must be used via the context manager as this allows it to manage thingslike transactions and deferred SQL (like creating ForeignKey constraints).

It exposes all possible operations as methods, that should be called inthe order you wish changes to be applied. Some possible operations or typesof change are not possible on all databases - for example, MyISAM does notsupport foreign key constraints.

If you are writing or maintaining a third-party database backend for Django,you will need to provide a SchemaEditor implementation in order to work with1.7's migration functionality - however, as long as your database is relativelystandard in its use of SQL and relational design, you should be able tosubclass one of the built-in Django SchemaEditor classes and just tweak thesyntax a little. Also note that there are a few new database features thatmigrations will look for: can_rollback_ddl andsupports_combined_alters are the most important.

Methods

execute()

  • BaseDatabaseSchemaEditor.execute(sql, params=[])[源代码]
  • Executes the SQL statement passed in, with parameters if supplied. Thisis a simple wrapper around the normal database cursors that allowscapture of the SQL to a .sql file if the user wishes.

create_model()

  • BaseDatabaseSchemaEditor.createmodel(_model)[源代码]
  • Creates a new table in the database for the provided model, along with anyunique constraints or indexes it requires.

delete_model()

  • BaseDatabaseSchemaEditor.deletemodel(_model)[源代码]
  • Drops the model's table in the database along with any unique constraintsor indexes it has.

add_index()

  • BaseDatabaseSchemaEditor.addindex(_model, index)[源代码]
  • Adds index to model’s table.

remove_index()

  • BaseDatabaseSchemaEditor.removeindex(_model, index)[源代码]
  • Removes index from model’s table.

alter_unique_together()

  • BaseDatabaseSchemaEditor.alterunique_together(_model, old_unique_together, new_unique_together)[源代码]
  • Changes a model's unique_together value; thiswill add or remove unique constraints from the model's table until they matchthe new value.

alter_index_together()

  • BaseDatabaseSchemaEditor.alterindex_together(_model, old_index_together, new_index_together)[源代码]
  • Changes a model's index_together value; thiswill add or remove indexes from the model's table until they match the newvalue.

alter_db_table()

  • BaseDatabaseSchemaEditor.alterdb_table(_model, old_db_table, new_db_table)[源代码]
  • Renames the model's table from old_db_table to new_db_table.

alter_db_tablespace()

  • BaseDatabaseSchemaEditor.alterdb_tablespace(_model, old_db_tablespace, new_db_tablespace)[源代码]
  • Moves the model's table from one tablespace to another.

add_field()

  • BaseDatabaseSchemaEditor.addfield(_model, field)[源代码]
  • Adds a column (or sometimes multiple) to the model's table to represent thefield. This will also add indexes or a unique constraintif the field has db_index=True or unique=True.

If the field is a ManyToManyField without a value for through, insteadof creating a column, it will make a table to represent the relationship. Ifthrough is provided, it is a no-op.

If the field is a ForeignKey, this will also add the foreign keyconstraint to the column.

remove_field()

  • BaseDatabaseSchemaEditor.removefield(_model, field)[源代码]
  • Removes the column(s) representing the field from the model's table, alongwith any unique constraints, foreign key constraints, or indexes caused bythat field.

If the field is a ManyToManyField without a value for through, it willremove the table created to track the relationship. Ifthrough is provided, it is a no-op.

alter_field()

  • BaseDatabaseSchemaEditor.alterfield(_model, old_field, new_field, strict=False)[源代码]
  • This transforms the field on the model from the old field to the new one. Thisincludes changing the name of the column (thedb_column attribute), changing the type of thefield (if the field class changes), changing the NULL status of the field,adding or removing field-only unique constraints and indexes, changing primarykey, and changing the destination of ForeignKey constraints.

The most common transformation this cannot do is transforming aManyToManyField into a normal Field or vice-versa; Django cannot do thiswithout losing data, and so it will refuse to do it. Instead,remove_field() and add_field() should be called separately.

If the database has the supports_combined_alters, Django will try anddo as many of these in a single database call as possible; otherwise, it willissue a separate ALTER statement for each change, but will not issue ALTERswhere no change is required (as South often did).

Attributes

All attributes should be considered read-only unless stated otherwise.

connection

  • SchemaEditor.connection
  • A connection object to the database. A useful attribute of the connection isalias which can be used to determine the name of the database beingaccessed.

This is useful when doing data migrations for migrations with multipledatabases.