1

Origin of question I'm recently working with django and became used to of Meta class in models, Serializers, and Forms.

My Understanding so far I learned that meta classes are used for creating classes.

When one class is defined, Python will go inside the class and collect all attributes and methods and store as dictionary, after that it searches for __metaclass__ attribute. If defined, it will use that class to create the defined class else it will use default object. Object is default class which is inherited to all classes, and this object class must have __metaclass__ which is type by default.

type class have __new__ and __init__ methods which is used to create classes.


My question What is the flow of creating a class when we declare Meta class inside definition of class

For example

class Transformer(models.Model):
    name = models.CharField(max_length=150, unique=True)

    class Meta:
        ordering = ('name',)

Where and When this Meta class is used?

Edit 1:
Cleared one thing that metaclasses and django Meta are different.
So Meta is just nested class of Transformer Model Class.

Question: Still my quesition is how this Meta class is used by Model Class?

TylerH
  • 20,799
  • 66
  • 75
  • 101
Parth
  • 101
  • 1
  • 6
  • 5
    Metaclasses and Django `Meta` are completely different things with unfortunately similar names. – user2357112 Jul 21 '22 at 07:26
  • is `Meta` a metaclass? or is it just a nested class of `Transformer`? – Joseph Asaf Gardin Jul 21 '22 at 07:45
  • `Meta` just needs to be an object with attributes, which allows you to configure the behavior. Conventionally a `class` declaration is the easiest way to create such an object inline. That’s all. Nothing to do with metaclasses. – deceze Jul 21 '22 at 08:06
  • 1
    refer [this](https://stackoverflow.com/questions/100003/what-are-metaclasses-in-python) link for better understanding – Hetvi Dec 20 '22 at 09:19

2 Answers2

1

Model Meta is basically the inner class of your model class. Model Meta is basically used to change the behavior of your model fields like changing order options,verbose_name_plural, and a lot of other options. It’s completely optional to add a Meta class to your model.

example:

class Category (models.Model):
    name = models.CharField(max_length=255)
    slug = models.SlugField(max_length=255, unique=True)

    def __str__(self):
    return self.name

    class Meta:
         verbose_name_plural= 'Categories' 
foysalf652
  • 208
  • 1
  • 10
1

As put in the comments: Python metaclasses are different from django metaclasses: Django just, for historical reasons, use the same terminology for the inner class where one annotates extra parameters about a class, where the primary members of the outer class are meant to correspond to fields in a model or form.

A Python metaclass, on the other hand, are what you are describing in your example, though you have checked some Python 2 documentation. In current Python, the metaclass is determined by passing the keyword argument "metaclas=" in the declaration of a new class, where the base classes go:

class MyClass(Base1, Base2, metaclass=MyMeta):
   ...

As far as I know it, the Django behavior had origin in which early versions of Django actually used a custom (Python) metaclass to annotate some of the parameters now used in the nested Meta - and in doing so, it took a shortcut of defining the metaclass inline inside the class body: instead of assigning the __metaclass__ name to an externally defined metaclass, as the usual for normal use, it would just define the class inplace: from the point of view of the language runtime, it would find the name __metaclass__ bound to a valid metaclass and use that to build the class.

Later versions, even in Python 2, modified this approach - the inner class was no longer the actual "metaclass" of the Model or Form (as the previous approach was clearly overkill).

jsbueno
  • 99,910
  • 10
  • 151
  • 209
  • ohk, thank you for your explanation. Correct me if I'm wrong __Meta in django is used because if attributes are directly written in models or Forms then django won't be able to differentiate betwen normal field attributes or optional attributes which i want to set like `ordering`.__ – Parth Jul 22 '22 at 04:48
  • yes - the reason of Django's nested "meta" is so that one can have a lot of other parameters/attributes about the model, in a way they won't conflict with any fields. – jsbueno Jul 22 '22 at 15:35