================``SchemaEditor``================.. module:: django.db.backends.base.schema.. class:: BaseDatabaseSchemaEditorDjango'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::with connection.schema_editor() as schema_editor: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 withDjango's migration functionality - however, as long as your database isrelatively standard in its use of SQL and relational design, you should be ableto subclass one of the built-in Django ``SchemaEditor`` classes and tweak thesyntax a little.Methods=======``execute()``-------------.. method:: BaseDatabaseSchemaEditor.execute(sql, params=())Executes the SQL statement passed in, with parameters if supplied. Thisis a wrapper around the normal database cursors that allows capture of the SQLto a ``.sql`` file if the user wishes.``create_model()``------------------.. method:: BaseDatabaseSchemaEditor.create_model(model)Creates a new table in the database for the provided model, along with anyunique constraints or indexes it requires.``delete_model()``------------------.. method:: BaseDatabaseSchemaEditor.delete_model(model)Drops the model's table in the database along with any unique constraintsor indexes it has.``add_index()``---------------.. method:: BaseDatabaseSchemaEditor.add_index(model, index)Adds ``index`` to ``model``’s table.``remove_index()``------------------.. method:: BaseDatabaseSchemaEditor.remove_index(model, index)Removes ``index`` from ``model``’s table.``rename_index()``------------------.. versionadded:: 4.1.. method:: BaseDatabaseSchemaEditor.rename_index(model, old_index, new_index)Renames ``old_index`` from ``model``’s table to ``new_index``.``add_constraint()``--------------------.. method:: BaseDatabaseSchemaEditor.add_constraint(model, constraint)Adds ``constraint`` to ``model``'s table.``remove_constraint()``-----------------------.. method:: BaseDatabaseSchemaEditor.remove_constraint(model, constraint)Removes ``constraint`` from ``model``'s table.``alter_unique_together()``---------------------------.. method:: BaseDatabaseSchemaEditor.alter_unique_together(model, old_unique_together, new_unique_together)Changes a model's :attr:`~django.db.models.Options.unique_together` value; thiswill add or remove unique constraints from the model's table until they matchthe new value.``alter_index_together()``--------------------------.. method:: BaseDatabaseSchemaEditor.alter_index_together(model, old_index_together, new_index_together)Changes a model's :attr:`~django.db.models.Options.index_together` value; thiswill add or remove indexes from the model's table until they match the newvalue.``alter_db_table()``--------------------.. method:: BaseDatabaseSchemaEditor.alter_db_table(model, old_db_table, new_db_table)Renames the model's table from ``old_db_table`` to ``new_db_table``.``alter_db_tablespace()``-------------------------.. method:: BaseDatabaseSchemaEditor.alter_db_tablespace(model, old_db_tablespace, new_db_tablespace)Moves the model's table from one tablespace to another.``add_field()``---------------.. method:: BaseDatabaseSchemaEditor.add_field(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. If``through`` 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()``------------------.. method:: BaseDatabaseSchemaEditor.remove_field(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. If``through`` is provided, it is a no-op.``alter_field()``-----------------.. method:: BaseDatabaseSchemaEditor.alter_field(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 (the:attr:`~django.db.models.Field.db_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 a``ManyToManyField`` into a normal Field or vice-versa; Django cannot do thiswithout losing data, and so it will refuse to do it. Instead,:meth:`.remove_field` and :meth:`.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.Attributes==========All attributes should be considered read-only unless stated otherwise.``connection``--------------.. attribute:: SchemaEditor.connectionA connection object to the database. A useful attribute of the connection is``alias`` which can be used to determine the name of the database beingaccessed.This is useful when doing data migrations for :ref:`migrations with multipledatabases <data-migrations-and-multiple-databases>`.