[Baypiggies] Trivial OOP pattern problem

David Ginsburg dav9dg at gmail.com
Fri Jun 15 09:01:00 CEST 2012


Hmm, so I just tried to actually run this and for some
reason inspect.getmembers(cairo.Context, predicate=inspect.ismethod)
returns an empty list.

Here's my ugly workaround:

def make_chainable_context(cls):

    def return_self_decorator(func):

        def wrapper(self, *args, **kwargs):
            to_return = func(self, *args, **kwargs)
            if to_return is None:
                to_return = self
            return to_return
        return wrapper

    #for method_name, method in inspect.getmembers(cairo.Context,
predicate=inspect.ismethod):
    for method_name, method in inspect.getmembers(cairo.Context):
        if not method_name.startswith('__'):
            setattr(cls, method_name, return_self_decorator(method))
    return cls

Pretty sure this accomplishes what you wanted :).

cheers,
David

On Thu, Jun 14, 2012 at 11:56 PM, David Ginsburg <dav9dg at gmail.com> wrote:

> Hello,
> The problem with this is if a method needs to return a value other than
> self, you break it.
> This is probably hacky, but you could accomplish what you want doing the
> following:
>
> import inspect
> import functools
>
> def make_chainable_context(cls):
>
>     def return_self_decorator(func):
>
>         def wrapper(self, *args, **kwargs):
>             to_return = func(self, *args, **kwargs)
>             if to_return is None:
>                 to_return = self
>             return to_return
>         return wrapper
>
>     for method_name, method in inspect.getmembers(cairo.Context,
> predicate=inspect.ismethod):
>         setattr(cls, method_name, return_self_decorator(method))
>     return cls
>
>
> @make_chainable_context
> class ChainableContext(cairo.Context):
>     pass
>
> This way methods that return something other than None are not broken.
>
> cheers,
> David
>
> On Thu, Jun 14, 2012 at 11:28 PM, Brian Palmer <bpalmer at gmail.com> wrote:
>
>> On Thu, Jun 14, 2012 at 10:52 PM, Ian Zimmerman <itz at buug.org> wrote:
>>
>>>
>>> Isaac> Hi, Why do you need each of the methods to return the instance?
>>> Isaac> Can you just wrap the method calls in a function and return the
>>> Isaac> instance?
>>>
>>> I am not married to the idea of a wrapper class, but I don't understand
>>> what you propose instead.  What would the example code look like under
>>> your scheme?
>>>
>>
>> Your initial solution seems like it'd work:
>> class Wrap(object):
>>   def __init__(self, ctx):
>>     self.ctx = ctx
>>
>>   def __getattr__(self, name):
>>     def myf(*args, **kwargs):
>>       getattr(self.ctx, name)(*args, **kwargs)
>>       return self
>>     return myf
>>
>> There are benefits to being less dynamic, but this might be good enough.
>>
>> _______________________________________________
>> Baypiggies mailing list
>> Baypiggies at python.org
>> To change your subscription options or unsubscribe:
>> http://mail.python.org/mailman/listinfo/baypiggies
>>
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/baypiggies/attachments/20120615/a1673a55/attachment.html>


More information about the Baypiggies mailing list