Nick Coghlan wrote:If you are not getting an exception when breaking this rule, my guess would be that your metaclasses are not inheriting from 'type', or else are not invoking type's __new__ method. The logic to trigger the exception lives in type's __new__ method - if that doesn't get invoked, you won't get the exception.
OK, I actually read the bug report - I think the 'invalid metaclass' exception should also be getting thrown in the case described there.
Py> class Meta1(type): pass ... Py> class Meta2(Meta1): pass ... Py> class MetaA(type): pass ... Py> class C1(object): ... __metaclass__ = Meta1 ... Py> class C2(C1): ... __metaclass__ = Meta2 ... Py> class C3(C2): ... __metaclass__ = Meta1 ... Py> type(C3) <class '__main__.Meta2'> Py>
'Meta1' is NOT a subclass of 'Meta2', yet the exception is not thrown. Instead, the explicitly requested metaclass has been silently replaced with a subclass. I think the OP is justified in calling that 'suprising'.
This is precisely the documented (in Guido's essay) behavior. That is, type.__new__ uses the "most derived" of the explicit metaclass and the __class__ attributes of the bases.
_______________________________________________ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com