Reputation: 13
With following code, I expect the output to be:
# meta.__new__
# meta.__new__
# meta.__init__
# Before instantiation of Entity
# meta.__call__
# __new__
# __init__
# __call__
#
Instead I got following output:
# meta.__new__
# meta.__new__
# meta.__init__
# Before instantiation of Entity
# meta.__call__
# __new__
# __init__
# Traceback (most recent call last):
# File "test.py", line 39, in <module>
# e(3,4)
# TypeError: 'NoneType' object is not callable
class MyMetaClass(type):
def __new__(cls, name, bases, dct):
print 'meta.__new__'
return super(MyMetaClass, cls).__new__(cls, name, bases, dct)
def __init__(cls, name, bases, dct):
print 'meta.__init__'
super(MyMetaClass, cls).__init__(name, bases, dct)
def __call__(self, *more):
print 'meta.__call__'
super(MyMetaClass, self).__call__(*more)
class Entity(object):
__metaclass__ = MyMetaClass
def __new__(cls, *args, **kwargs):
print '__new__'
return super(Entity, cls).__new__(cls, *args, **kwargs)
def __init__(self, x, y):
print '__init__'
self.x, self.y = x, y
def __call__(self, x, y):
print '__call__'
self.x, self.y = x, y
if __name__ == '__main__':
print 'Before instantiation of Entity'
e = Entity(1,2)
e(3,4)
Upvotes: 1
Views: 108
Reputation: 121964
Note that MyMetaClass.__call__
, which is being invoked on creation and instantiation of e
, doesn't actually return anything, hence e is None
afterwards. The minimal fix is therefore to:
class MyMetaClass(type):
...
def __call__(self, *more):
print 'meta.__call__'
return super(MyMetaClass, self).__call__(*more)
# ^ add return
But without an explanation of why you've implemented __new__
and __init__
and __call__
on the metaclass, including a less abstract example, it's hard to provide advice on what the most appropriate fix might be.
Upvotes: 1