The algorithme in DeclarativeFieldsMetaclass __new__ method

1. class DeclarativeFieldsMetaclass(MediaDefiningClass):
2.   
3.     def __new__(mcs, name, bases, attrs):
4.         # Collect fields from current class and remove them from attrs.
5.         attrs["declared_fields"] = {
6.             key: attrs.pop(key)
7.             for key, value in list(attrs.items())
8.             if isinstance(value, Field)
9.         }

10.         new_class = super().__new__(mcs, name, bases, attrs)

11.         # Walk through the MRO.
12.         declared_fields = {}
13.         for base in reversed(new_class.__mro__):
14.             # Collect fields from base class.
15.             if hasattr(base, "declared_fields"):
16.                 declared_fields.update(base.declared_fields)

17.             # Field shadowing.
18.             for attr, value in base.__dict__.items():
19.                 if value is None and attr in declared_fields:
20.                     declared_fields.pop(attr)

21.         new_class.base_fields = declared_fields
22.         new_class.declared_fields = declared_fields

23.         return new_class

the __new__ method (above) in DeclarativeFieldsMetaclass collect Fields declared on all base (parent) classes. to achieve that it goes through the entire __mro__ list (line 13) :

13.         for base in reversed(new_class.__mro__):
14.             # Collect fields from base class.
15.             if hasattr(base, "declared_fields"):
16.                 declared_fields.update(base.declared_fields)

I’m wondering whay ?? :thinking: :thinking:
is it not possible to collectte fileds only form the parent classes (the first level of inheretence)?? since those parent classes shoud have aleredy collected fileds from thers parents. So whay ruuning through the entire __mro__ list ??

I am not sure. Two ways you could answer this question:

  1. Use git blame to see when those lines changed - the associated commit, and pull request/ticket, may reveal why.
  2. Comment out the line and run the test suite. For any feature in Django, there’s normally a good test.

If no tests fail, and you can’t find any reason, you may have found a way to simplify Django…