Opened 3 weeks ago

Closed 2 weeks ago

Last modified 2 weeks ago

#37254 closed Bug (fixed)

Fields.E323 check for mixing python & database-level on_delete values not checked on implicit M2M through tables

Reported by: Jacob Walls Owned by: Mariusz Felisiak
Component: Database layer (models, ORM) Version: 6.1
Severity: Release blocker Keywords:
Cc: Mariusz Felisiak Triage Stage: Ready for checkin
Has patch: yes Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description

This set of models with an explicit through= model raises Fields.E323 as expected:

from django.contrib.auth.models import User
from django.db import models


class Hobby(models.Model): ...


class Person(models.Model):
    user = models.ForeignKey(User, on_delete=models.DB_CASCADE)
    hobbies = models.ManyToManyField(Hobby, through=HobbyXPerson)


class HobbyXPerson(models.Model):
    hobby = models.ForeignKey(Hobby, on_delete=models.CASCADE)
    person = models.ForeignKey(Person, on_delete=models.CASCADE)
    
    class Meta:
        constraints = [
            models.UniqueConstraint(
                fields=["person", "hobby"], name="unique_person_hobby"
            )
        ]
ERRORS:
app.HobbyXPerson.person: (fields.E323) Field specifies Python-level on_delete variant, but referenced model uses database-level variant.
	HINT: Use either database or Python on_delete variants uniformly in the references chain.

But this one does not:

from django.contrib.auth.models import User
from django.db import models


class Hobby(models.Model): ...


class Person(models.Model):
    user = models.ForeignKey(User, on_delete=models.DB_CASCADE)
    hobbies = models.ManyToManyField(Hobby)

Deletions are still collected in python:

def run():
    user = User.objects.create(username='me')
    person = Person.objects.create(user=user)
    person.hobbies.add(Hobby.objects.create())
    person.delete()
DELETE
FROM "app_person_hobbies"
WHERE "app_person_hobbies"."person_id" IN (1)
DELETE
FROM "app_person"
WHERE "app_person"."id" IN (1)

Change History (7)

comment:1 by Mariusz Felisiak, 3 weeks ago

Owner: set to Mariusz Felisiak
Status: newassigned
Triage Stage: UnreviewedAccepted

comment:2 by Mariusz Felisiak, 3 weeks ago

Has patch: set

comment:3 by Sarah Boyce, 2 weeks ago

Patch needs improvement: set

comment:4 by Mariusz Felisiak, 2 weeks ago

Patch needs improvement: unset

comment:5 by Jacob Walls, 2 weeks ago

Triage Stage: AcceptedReady for checkin

comment:6 by GitHub <noreply@…>, 2 weeks ago

Resolution: fixed
Status: assignedclosed

In c6be0bf:

Fixed #37254 -- Added fields.E323 for models referenced by ManyToManyFields.

Thanks Jacob Walls and Sarah Boyce for reviews.

comment:7 by Mariusz Felisiak <felisiak.mariusz@…>, 2 weeks ago

In b26f3c69:

[6.1.x] Fixed #37254 -- Added fields.E323 for models referenced by ManyToManyFields.

Thanks Jacob Walls and Sarah Boyce for reviews.
Backport of c6be0bf3bb744d234947cefd6def9f31d9655800 from main

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