0

I have a object like:

class Foo(object):
    def __init__(self,instance):
        self.instance = instance

with

>>> instance = SomeOtherObject()
>>> f = Foo(instance)

I want to be able to do

>>> f.some_method()

and have the following call,

>>> f.instance.some_method()

For complicated reasons, I cannot simply chain the attributes as in the above. I need to dynamically create an instance function on f with the same function signature as the embedded instance. That is, I need to do f.some_method() and then dynamically create the some_method instance-method for the f instance when it is invoked that pushes some_method down to the embedded object instance.

I hope that made sense. This is for Python 2.7. Any help appreciated.

1
  • To create a Foo in your code, one must pass an instance of something else as an argument, so f = Foo() would cause an error. Commented Aug 5, 2016 at 1:18

2 Answers 2

3

Write a __getattr__() method for your proxy class. This will be called when an attribute is accessed that doesn't exist on your instance. Return your contained object's attribute of the same name (or a wrapper if you insist, but there's no need if you just want to call the contained object's method and don't need to do anything else). Bonus: works with data as well as callables.

def __getattr__(self, name):
    return getattr(self.instance, name)

Does not work with __ methods, however.

Sign up to request clarification or add additional context in comments.

Comments

1

You should look at the wrapt module. It is purpose built for creating transparent object proxy where you can selectively override certain aspects of the wrapped object. For example:

class Test(object):
    def some_method(self):
        print 'original'

import wrapt

proxy = wrapt.ObjectProxy(Test())
proxy.some_method()

print

class TestWrapper(wrapt.ObjectProxy):
    def some_method(self):
        self.__wrapped__.some_method()
        print 'override'

wrapper = TestWrapper(Test())
wrapper.some_method()

This yields:

original

original
override

The default behaviour of the ObjectProxy class is to proxy all method calls or attribute access. Updating attributes via the proxy will also update the wrapped object. Works for special __ methods and lots of other stuff as well.

For details on wrapt see:

Specific details on the object proxy can be found in:

There are so many traps and pitfalls with doing this correctly, so recommended you use wrapt if you can.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.