Opened 7 years ago

Closed 7 years ago

#28803 closed Bug (duplicate)

When renaming foreign key indexes don't get renamed which breaks next migrations

Reported by: Jacek Bzdak Owned by: nobody
Component: Migrations Version: 1.11
Severity: Normal Keywords:
Cc: Triage Stage: Unreviewed
Has patch: no Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description

Here is what I did. I have following models:

class ReferencedModel(models.Model):
   pass


class SecondReferencedModel(models.Model):
   pass


class ReferenceeModel(models.Model):
  child = models.ForeignKey(ReferencedModel, default=None, on_delete=models.CASCADE)

I want to swichch ReferenceeModel.child to SecondReferencedModel.

I want to do it by:

1) Renaming ReferenceeModel.child_old
2) Adding ReferenceeModel.child that points to proper model
3) Some RunPython magic
4) Delete ReferenceeModel.child_old

Actual bug:

class Migration(migrations.Migration):

    initial = True

    dependencies = [
    ]

    operations = [
        migrations.CreateModel(
            name='ReferencedModel',
            fields=[
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
            ],
        ),
        migrations.CreateModel(
            name='SecondReferencedModel',
            fields=[
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
            ],
        ),
        migrations.CreateModel(
            name='ReferenceeModel',
            fields=[
                ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
                ('child', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='index_error.ReferencedModel')),
            ],
        ),
    ]

class Migration(migrations.Migration):

    dependencies = [
        ('index_error', '0001_initial'),
    ]

    operations = [
        migrations.RenameField(
            model_name='referenceemodel',
            old_name='child',
            new_name='child_copy',
        ),
    ]


class Migration(migrations.Migration):

    dependencies = [
        ('index_error', '0002_auto_20171116_1505'),
    ]

    operations = [
        migrations.AddField(
            model_name='referenceemodel',
            name='child',
            field=models.ForeignKey(default=None, on_delete=django.db.models.deletion.CASCADE, to='index_error.SecondReferencedModel'),
        ),
    ]

Third migration explodes with following error:

django.db.utils.ProgrammingError: relation "index_error_referenceemodel_child_id_59ba6fc6" already exist

Which is due to the

1) Field child = models.ForeignKey(ReferencedModel, ...) generates postgresql index named index_error_referenceemodel_child_id_59ba6fc6
2) RenameField operation doesn't update index name (but changes field name)
3) When I try to create new field index names clash.

My setup:

  • Django 1.11 (also broken in 2.0)
  • postgresql database

Attachments (1)

index_migration.zip (16.7 KB ) - added by Jacek Bzdak 7 years ago.
Project that reproduces the issue

Download all attachments as: .zip

Change History (4)

by Jacek Bzdak, 7 years ago

Attachment: index_migration.zip added

Project that reproduces the issue

comment:1 by Jacek Bzdak, 7 years ago

Workaround for this issue is, to add two Alter field migratons (before and after rename), one takes down the index other recreates it --- if you have large dataset probably you should just rename the index manually.

comment:2 by Jacek Bzdak, 7 years ago

Type: UncategorizedBug

comment:3 by Tim Graham, 7 years ago

Resolution: duplicate
Status: newclosed

Looks like a duplicate of #23577.

Note: See TracTickets for help on using tickets.
Back to Top