How to make a proxy object behave like the integer it wraps?
<p>I want to create a proxy class that wraps an <code>int</code> for thread-safe access. In contrast to the built-in type, the proxy class is mutable, so that it can be incremented in-place. Now, I want to use that class just as a normal integer from the outside. Usually, Python's <code>__getattr__</code> makes it very easy to forward attribute access to the inner object:</p>

<pre><code>class Proxy:

    def __init__(self, initial=0):
        self._lock = threading.Lock()
        self._value = initial

    def increment(self):
        with self._lock:
            self._value += 1

    def __getattr__(self, name):
        return getattr(self._value, name)
</code></pre>

<p>However, <a href="http://stackoverflow.com/q/33824228/1079110"><code>__getattr__</code> does not get triggered for magic methods</a> like <code>__add__</code>, <code>__rtruediv__</code>, etc that I need for the proxy to behave like an integer. Is there a way to generate those methods automatically, or otherwise forward them to the wrapped integer object?</p>

<p>The blog post linked by <a href="http://stackoverflow.com/users/5378816/vpfb">@VPfB</a> in the <a href="http://stackoverflow.com/questions/39186692/how-to-make-a-proxy-object-behave-like-the-integer-it-wraps/39190081#comment65719596_39186692">comments</a> has a more generic and thorough solution to proxying dunder methods for builtin types, but here's a simplified and rather brutish example for the same. I hope it helps in understanding how to create such forwarding methods.</p>

<pre><code>import threading
import numbers


def _proxy_slotted(name):
    def _proxy_method(self, *args, **kwgs):
        return getattr(self._value, name)(*args, **kwgs)
    # Not a proper qualname, but oh well
    _proxy_method.__name__ = _proxy_method.__qualname__ = name
    return _proxy_method

# The list of abstract methods of numbers.Integral
_integral_methods = """
    __abs__ __add__ __and__ __ceil__ __eq__ __floor__
    __floordiv__ __int__ __invert__ __le__ __lshift__
    __lt__ __mod__ __mul__ __neg__ __or__ __pos__ __pow__
    __radd__ __rand__ __rfloordiv__ __rlshift__ __rmod__
    __rmul__ __ror__ __round__ __rpow__ __rrshift__
    __rshift__ __rtruediv__ __rxor__ __truediv__ __trunc__
    __xor__""".split()

# The dunder, aka magic methods
_Magic = type('_Magic', (),
              {name: _proxy_slotted(name)
               for name in _integral_methods})


class IntProxy(_Magic, numbers.Integral):
    """
    &gt;&gt;&gt; res = IntProxy(1) + 1
    &gt;&gt;&gt; print(type(res), res)
    &lt;class 'int'&gt; 2
    &gt;&gt;&gt; print(IntProxy(2) / 3)
    0.6666666666666666
    """

    def __init__(self, initial=0, Lock=threading.Lock):
        self._lock = Lock()
        self._value = initial

    def increment(self):
        with self._lock:
            self._value += 1

    def __getattr__(self, name):
        return getattr(self._value, name)
</code></pre>

python python-3.x proxy