Add common database backend support for changing field types.

Review Request #12232 — Created April 8, 2022 and submitted

Information

Django Evolution
release-2.x

Reviewers

This introduces new methods on BaseEvolutionOperations for changing a
field type:

  • change_column_type(): Orchestrates changing the type of a field,
    dropping/re-adding any constraints and updating the types of any
    fields pointing to the changed field.

  • get_change_column_type_sql(): Returns backend-specific SQL for
    changing the type of any given field.

Along with a new capability attribute, change_column_type_sets_attrs,
which states whether get_change_column_type_sql() will also handle
setting all the attributes for the field definition. If False,
attributes need to be set in a separate change_column_attrs() call.

The basic strategy for changing a field type is:

  1. Any constraints pointing to the changed field must be dropped, in
    order to avoid issues with incompatible data types between the
    referring fields and the changed field.

  2. The field type can then safely be changed. Depending on the database
    backend, the command for this may include the entire field definition
    (NOT NULL, VARCHAR(...), etc.), or it may not (requiring that
    these changes are made separately, if needed). This part is not
    currently implemented by any backends.

  3. Any fields referring to the changed field need to be updated to match
    the field type.

  4. Constraints dropped in step 1 can then be restored.

BaseEvolutionOperations takes care of all of this by default, leaving
most backends responsible only for the capability attribute and the
implementation of get_change_column_type_sql(). Subclasses are free
to override the entire process, if needed.

Upcoming changes will implement the per-database support, the
orchestration in ChangeField and related objects, and the test suite.

Tested along with the other upcoming changes for this feature. All unit
tests pass on all supported databases and versions of Django.

Summary ID
Add common database backend support for changing field types.
This introduces new methods on `BaseEvolutionOperations` for changing a field type: * `change_column_type()`: Orchestrates changing the type of a field, dropping/re-adding any constraints and updating the types of any fields pointing to the changed field. * `get_change_column_type_sql()`: Returns backend-specific SQL for changing the type of any given field. Along with a new capability attribute, `change_column_type_sets_attrs`, which states whether `get_change_column_type_sql()` will also handle setting all the attributes for the field definition. If `False`, attributes need to be set in a separate `change_column_attrs()` call. The basic strategy for changing a field type is: 1. Any constraints pointing to the changed field must be dropped, in order to avoid issues with incompatible data types between the referring fields and the changed field. 2. The field type can then safely be changed. Depending on the database backend, the command for this may include the entire field definition (`NOT NULL`, `VARCHAR(...)`, etc.), or it may not (requiring that these changes are made separately, if needed). This part is not currently implemented by any backends. 3. Any fields referring to the changed field need to be updated to match the field type. 4. Constraints dropped in step 1 can then be restored. `BaseEvolutionOperations` takes care of all of this by default, leaving most backends responsible only for the capability attribute and the implementation of `get_change_column_type_sql()`. Subclasses are free to override the entire process, if needed. Upcoming changes will implement the per-database support, the orchestration in `ChangeField` and related objects, and the test suite.
c038dd47612b07d091ccbb4f42ecb639c4e1f123
david
  1. Ship It!
  2. 
      
chipx86
Review request changed
Status:
Completed
Change Summary:
Pushed to release-2.x (3a20237)