class Meta(type):
    @classmethod
    def __prepare__(metacls, name, bases, **kwds):
        """Prepare the namespace in which the class will be executed."""
        print(
            "Meta.__prepare__(",
            f"{metacls=},",
            f"{name=},",
            f"{bases=},",
            f"{kwds=}) -> {{}}",
            sep="\n    ",
        )
        return {}

    # __new__() is a static method (special-cased so you need not declare it as such)
    def __new__(cls, name, bases, namespace, **kwds):
        """The class body is executed in a new namespace and the class name is
        bound locally to the result of type(name, bases, namespace).
        """
        print(
            "\nMeta.__new__(",
            f"{cls=},",
            f"{name=},",
            f"{bases=},",
            f"{namespace=}",
            f"{kwds=})",
            sep="\n    ",
            end=" ",
        )
        returns = type.__new__(cls, name, bases, namespace)
        print(f"-> {returns}\n")
        return returns

    def __init__(self, name, bases, namespace, **kwds):
        """This is the actual creation of the class !

        As a class is an instance of its type."""
        print(
            "Meta.__init__(",
            f"{self=},",
            f"{name=},",
            f"{bases=},",
            f"{namespace=},",
            f"{kwds=})",
            sep="\n    ",
            end="\n\n"
        )


class Classe(metaclass=Meta):

    print("\nAfter Meta.__prepare__ is called, the interpreter executes the class body "
          "like:")
    print("    exec(body, globals(), ns)")
    print("with `ns` the dict returned from __prepare__")


    def __new__(cls, *args, **kwargs):
        print(f"Classe.__new__({cls=}, {args=}, {kwargs=})")
        returns = object.__new__(cls)
        print(f"    returns {returns}")
        return returns

    def __init__(self, *args, **kwargs):
        print(f"Classe.__init__({self=}, {args=}, {kwargs=})")


print("Will now instantiate a Classe()")

Classe()
