When I derive the BaseClass by the ChildClass, the BaseMetaClass.__new__(...) is run twice. First with the keywordarg "foo" and second time with "bar".
Is it possible to override "foo" with "bar" before it is executed in the first place.
I don't care if it is run twice but in the first execution it should have the value of "bar".
class BaseMetaClass(type):
def __new__(cls, name, bases, attrs, *args, **kwargs):
# do something with attrs here
return super().__new__(cls, name, bases, attrs)
class BaseClass(keywordarg="foo", metaclass=BaseMetaClass):
pass
class ChildClass(BaseClass, keywordarg="bar"):
pass
Why am I trying this:
I am trying this because I am figuring out how to override/ manipulate a decorator that registers a service.
Things I have tried in addition
I have already tried __prepare__ which did not lead to a the outcome I was hoping for.
I also tried following which seems not to be a valid syntax
class ChildClass(BaseClass(keywordarg="bar)):
In the code you provide,
BaseMetaclass.__new__is executed exactly once forBaseClassand then, exact once forChildClass.I can't imagine why you think it could be different. THe creation of
ChildClassitself will only run the metaclass__new__code once, with the custom named arguments passed in that child class.That is easy to visualize by simply adding a print call to to
__new__:And running this snippet outputs:
If you don't want "keywordarg" to be set when creating "BaseClass" at all, just don't pass it as a named argument. Otherwise, the code is working as expcted, and
BaseMetaClass.__new__is executed a single time, with the argumentbar, when the class is created.Python can't "know beforehand" that ChildClass will inherit from BaseClass and change "keywordarg" when creating BaseClass - and even if it could be possible (it could by reading the source file itself and resolving references, essentially interpreting the Python code before it would be executed), what should it do if more than one class would derive from "BaseClass"? WHich of the children parameters it should pick?
You mention you are trying this in order to "register a service" - it looks like you have a "XY" problem: what you are trying to do is not how class creation, customized or not, work. Just spell what you are actually trying to achieve there, not this one step you thought you might need.