D
Demian Brecht
Hey all,
Using bases in a metaclass, I've been able to easily figure out when
an attribute is being added to an instance of a class. However, what
I'm /actually/ looking to do is to intercept when attributes are being
added to a class (not an instance of). I thought that I'd be able to
do so by passing in a subclass of dict to type.__new__ of the
metaclass's __new__ and implementing a custom __setitem__, but
apparently that's not the case.
If you're curious as to why I'm doing this, I'm trying to clean up
https://gist.github.com/demianbrecht/6944269 and get rid of the
late_bind method there in favour of using the appropriate magic
methods. The intention is to piggyback off of abc's
__abstractmethods__ in order to implement a "looks_like" method that
checks that one class conforms to an unrelated class's interface
rather than using inheritance to enforce interface implementations at
class creation time. This is /only/ intended to be a proof of concept
for demonstration purposes and nothing that I'd ever actually
implement, so no need for flaming the concept
# test.py
class Dict(dict):
def __setattr__(self, key, value):
print 'Dict.__setattr__'
dict.__setattr__(self, key, value)
def __setitem__(self, key, value):
print 'Dict.__setitem__'
dict.__setitem__(self, key, value)
class Bar(object):
def __setattr__(self, key, value):
print 'Bar.__setattr__'
object.__setattr__(self, key, value)
class metafoo(type):
def __new__(mcls, name, bases, dct):
return type.__new__(mcls, name, (Bar,), Dict(dct))
class Foo(object):
__metaclass__ = metafoo
# I'm expecting Dict.__setattr__ here, but... *crickets*
Am I missing something here, or do I just have to live with what I
currently have in my gist?
Thanks,
Using bases in a metaclass, I've been able to easily figure out when
an attribute is being added to an instance of a class. However, what
I'm /actually/ looking to do is to intercept when attributes are being
added to a class (not an instance of). I thought that I'd be able to
do so by passing in a subclass of dict to type.__new__ of the
metaclass's __new__ and implementing a custom __setitem__, but
apparently that's not the case.
If you're curious as to why I'm doing this, I'm trying to clean up
https://gist.github.com/demianbrecht/6944269 and get rid of the
late_bind method there in favour of using the appropriate magic
methods. The intention is to piggyback off of abc's
__abstractmethods__ in order to implement a "looks_like" method that
checks that one class conforms to an unrelated class's interface
rather than using inheritance to enforce interface implementations at
class creation time. This is /only/ intended to be a proof of concept
for demonstration purposes and nothing that I'd ever actually
implement, so no need for flaming the concept
# test.py
class Dict(dict):
def __setattr__(self, key, value):
print 'Dict.__setattr__'
dict.__setattr__(self, key, value)
def __setitem__(self, key, value):
print 'Dict.__setitem__'
dict.__setitem__(self, key, value)
class Bar(object):
def __setattr__(self, key, value):
print 'Bar.__setattr__'
object.__setattr__(self, key, value)
class metafoo(type):
def __new__(mcls, name, bases, dct):
return type.__new__(mcls, name, (Bar,), Dict(dct))
class Foo(object):
__metaclass__ = metafoo
# I'm expecting Dict.__setattr__ here, but... *crickets*
Am I missing something here, or do I just have to live with what I
currently have in my gist?
Thanks,