| 56 | """ |
| 57 | |
| 58 | def decorator(decorated): |
| 59 | docstring_components = [] |
| 60 | |
| 61 | # collect docstrings and docstring templates |
| 62 | for docstring in docstrings: |
| 63 | if docstring is None: |
| 64 | continue |
| 65 | if hasattr(docstring, "_docstring_components"): |
| 66 | docstring_components.extend( |
| 67 | docstring._docstring_components |
| 68 | ) |
| 69 | elif isinstance(docstring, str) or docstring.__doc__: |
| 70 | docstring_components.append(docstring) |
| 71 | |
| 72 | # append the callable's docstring last |
| 73 | if decorated.__doc__: |
| 74 | docstring_components.append(textwrap.dedent(decorated.__doc__)) |
| 75 | |
| 76 | params_applied = [ |
| 77 | component.format(**params) |
| 78 | if isinstance(component, str) and len(params) > 0 |
| 79 | else component |
| 80 | for component in docstring_components |
| 81 | ] |
| 82 | |
| 83 | decorated.__doc__ = "".join( |
| 84 | [ |
| 85 | component |
| 86 | if isinstance(component, str) |
| 87 | else textwrap.dedent(component.__doc__ or "") |
| 88 | for component in params_applied |
| 89 | ] |
| 90 | ) |
| 91 | |
| 92 | decorated._docstring_components = ( |
| 93 | docstring_components |
| 94 | ) |
| 95 | return decorated |
| 96 | |
| 97 | return decorator |
| 98 | |