Inherit docstrings in Python class inheritance
You're not the only one! There was a discussion on comp.lang.python
about this a while ago, and a recipe was created. Check it out here.
"""doc_inherit decoratorUsage:class Foo(object): def foo(self): "Frobber" passclass Bar(Foo): @doc_inherit def foo(self): pass Now, Bar.foo.__doc__ == Bar().foo.__doc__ == Foo.foo.__doc__ == "Frobber""""from functools import wrapsclass DocInherit(object): """ Docstring inheriting method descriptor The class itself is also used as a decorator """ def __init__(self, mthd): self.mthd = mthd self.name = mthd.__name__ def __get__(self, obj, cls): if obj: return self.get_with_inst(obj, cls) else: return self.get_no_inst(cls) def get_with_inst(self, obj, cls): overridden = getattr(super(cls, obj), self.name, None) @wraps(self.mthd, assigned=('__name__','__module__')) def f(*args, **kwargs): return self.mthd(obj, *args, **kwargs) return self.use_parent_doc(f, overridden) def get_no_inst(self, cls): for parent in cls.__mro__[1:]: overridden = getattr(parent, self.name, None) if overridden: break @wraps(self.mthd, assigned=('__name__','__module__')) def f(*args, **kwargs): return self.mthd(*args, **kwargs) return self.use_parent_doc(f, overridden) def use_parent_doc(self, func, source): if source is None: raise NameError, ("Can't find '%s' in parents"%self.name) func.__doc__ = source.__doc__ return funcdoc_inherit = DocInherit
You can concatenate the docstrings easily:
class Foo(object): """ Foo Class. This class foos around. """ passclass Bar(Foo): """ Bar class, children of Foo Use this when you want to Bar around. parent: """ __doc__ += Foo.__doc__ pass
However, that is useless. Most documentation generation tool (Sphinx and Epydoc included) will already pull parent docstring, including for methods. So you don't have to do anything.
Not particularly elegant, but simple and direct:
class X(object): """This class has a method foo().""" def foo(): passclass Y(X): __doc__ = X.__doc__ + ' Also bar().' def bar(): pass
Now:
>>> print Y.__doc__This class has a method foo(). Also bar().