[5.1.x] Fixed #34881 -- Fixed a crash when renaming a model with multiple ManyToManyField.through references on SQLite.

Thank you to dennisvang for the report and Jase Hackman for the test.

Co-authored-by: Jase Hackman <jase.hackman@zapier.com>

Backport of e99187e5c9 from main.
This commit is contained in:
Anže Pečar 2024-06-13 16:41:50 +02:00 committed by Sarah Boyce
parent dbd1a8bd41
commit 48382a2ff6
2 changed files with 84 additions and 1 deletions

View File

@ -460,11 +460,11 @@ class RenameModel(ModelOperation):
model = new_model
related_key = (app_label, self.new_name_lower)
else:
model = related_object.related_model
related_key = (
related_object.related_model._meta.app_label,
related_object.related_model._meta.model_name,
)
model = to_state.apps.get_model(*related_key)
to_field = to_state.apps.get_model(*related_key)._meta.get_field(
related_object.field.name
)

View File

@ -1345,6 +1345,89 @@ class OperationTests(OperationTestBase):
ponyrider = PonyRider.objects.create()
ponyrider.riders.add(jockey)
def test_rename_m2m_field_with_2_references(self):
app_label = "test_rename_multiple_references"
project_state = self.apply_operations(
app_label,
ProjectState(),
operations=[
migrations.CreateModel(
name="Person",
fields=[
(
"id",
models.BigAutoField(
auto_created=True,
primary_key=True,
serialize=False,
verbose_name="ID",
),
),
("name", models.CharField(max_length=255)),
],
),
migrations.CreateModel(
name="Relation",
fields=[
(
"id",
models.BigAutoField(
auto_created=True,
primary_key=True,
serialize=False,
verbose_name="ID",
),
),
(
"child",
models.ForeignKey(
on_delete=models.CASCADE,
related_name="relations_as_child",
to="test_rename_multiple_references.person",
),
),
(
"parent",
models.ForeignKey(
on_delete=models.CASCADE,
related_name="relations_as_parent",
to="test_rename_multiple_references.person",
),
),
],
),
migrations.AddField(
model_name="person",
name="parents_or_children",
field=models.ManyToManyField(
blank=True,
through="test_rename_multiple_references.Relation",
to="test_rename_multiple_references.person",
),
),
],
)
Person = project_state.apps.get_model(app_label, "Person")
Relation = project_state.apps.get_model(app_label, "Relation")
person1 = Person.objects.create(name="John Doe")
person2 = Person.objects.create(name="Jane Smith")
Relation.objects.create(child=person2, parent=person1)
self.assertTableExists(app_label + "_person")
self.assertTableNotExists(app_label + "_personfoo")
self.apply_operations(
app_label,
project_state,
operations=[
migrations.RenameModel(old_name="Person", new_name="PersonFoo"),
],
)
self.assertTableNotExists(app_label + "_person")
self.assertTableExists(app_label + "_personfoo")
def test_add_field(self):
"""
Tests the AddField operation.