Source code documentation

Configuring sphinx

Sphinx lets you document your Python code in a very versatile way. Moreover, it can find your code docstrings and automatically generate documentation for you. Finally, it can generate class diagrams. Awesome right?! So let’s see how to do this.

See also

If you never used sphinx before, please follow the guide Getting started.

Changing the conf.py file

First you have to configure sphinx by adding some information on the conf.py file which you should find in the /docs/source folder.

Python path configuration

Sphinx must know where to search for your code. Because it will search on the Python path, you have 2 options:

  • Install your project with pip before building the documentation (you have to repeat this every time you make changes)
  • Inject your project source code directly in the Python path by changing the conf.py file
# If extensions (or modules to document with autodoc) are in another directory,
# add these directories to sys.path here. If the directory is relative to the
# documentation root, use os.path.abspath to make it absolute, like shown here.

sys.path.append(os.path.abspath('../../myproject'))
sys.path.append(os.path.abspath('../../'))

# Also import any other stuff you need here
from pysettings import conf; conf += 'pyforms_generic_editor.settings'

Add extensions for auto generated documentation and diagrams

If you followed our guide, you should already have the autodoc extension. In that case, just add the graphviz and the inheritance_diagram extensions.

extensions = [
    'sphinx.ext.autodoc',
    'sphinx.ext.viewcode',
    'sphinx.ext.intersphinx',
    'sphinx.ext.graphviz',
    'sphinx.ext.inheritance_diagram',
]

See also

You will need to install the Graphviz package on your system.

On Mac OSX: brew install graphviz

On Ubuntu: apt-get install graphviz

Writing documentation

Writing documentation can be done in one of the following ways:

Manualy adding code directives

You can document your entire code manually with sphinx.

For example, the following sphinx code

.. py:class:: CommAdpater

        Implement communication details

        .. py:method:: send_message(self, sender, recipient, message_body, [priority=1])

           Send a message to a recipient

           :param str sender: The person sending the message
           :param str recipient: The recipient of the message
           :param str message_body: The body of the message
           :param priority: The priority of the message, can be a number 1-5
           :type priority: integer or None
           :return: the message id
           :rtype: int
           :raises ValueError: if the message_body exceeds 160 characters
           :raises TypeError: if the message_body is not a basestring

would generate this:

class CommAdpater

Implement communication details

send_message(self, sender, recipient, message_body[, priority=1])

Send a message to a recipient

Parameters:
  • sender (str) – The person sending the message
  • recipient (str) – The recipient of the message
  • message_body (str) – The body of the message
  • priority (integer or None) – The priority of the message, can be a number 1-5
Returns:

the message id

Return type:

int

Raises:
  • ValueError – if the message_body exceeds 160 characters
  • TypeError – if the message_body is not a basestring

See also

You can find more information on this on the sphinx documentation page.

http://www.sphinx-doc.org/en/latest/domains.html#the-python-domain

Automatically extract docstrings from your code

Documenting your entire code manually can be a pain in the neck. Moreover, if you already included docstrings during development time, you would have to repeat this task and have to maintain documentation on two places.

A much better approach is to use the sphinx extension for discovering your source code structure and automatically extract docstrings from it.

Generating an inheritance diagram

.. inheritance-diagram:: pycontrolgui.models.experiment.experiment_uibusy
    :parts: 1

Auto extracting docstrings from source code

.. automodule:: pycontrolgui.models.experiment.experiment_window
    :members:
    :show-inheritance:
    :private-members:

You can see a nice example of the usage of the autodoc, graphviz and inheritance extensions for the experiment_window.py module under the pycontrol-gui project: