Search code examples
pythonpython-3.2functools

What are "Bootstrap issues" of functionls wraps decorator?


Python 3.2 introduces a new function recursive_repr in reprlib module.

When I looked into the source code I found this code:

def recursive_repr(fillvalue='...'):
    'Decorator to make a repr function return fillvalue for a recursive call'

    def decorating_function(user_function):
        repr_running = set()

        def wrapper(self):
            key = id(self), get_ident()
            if key in repr_running:
                return fillvalue
            repr_running.add(key)
            try:
                result = user_function(self)
            finally:
                repr_running.discard(key)
            return result

        # Can't use functools.wraps() here because of bootstrap issues
        wrapper.__module__ = getattr(user_function, '__module__')
        wrapper.__doc__ = getattr(user_function, '__doc__')
        wrapper.__name__ = getattr(user_function, '__name__')
        wrapper.__annotations__ = getattr(user_function, '__annotations__', {})
        return wrapper

    return decorating_function

What I didn't understand is what are Bootstrap issues and why can't @wraps(user_function) be applied to wrapper?


Solution

  • It looks to me like the "bootstrap issues" comes from a circular dependency. In this case, functools imports collections, which in turn imports reprlib. If reprlib tried to import functools.wraps, it would implicitly try to import itself, which would not work. The Python programming FAQ (2.7, but I don't think this has changed since) says that circular imports will fail when modules use the from module import function form, which these modules do.