{ "cells": [ { "cell_type": "markdown", "id": "a2586f22", "metadata": {}, "source": [ "# Sphinx Autodoc (Optional)" ] }, { "cell_type": "markdown", "id": "3136a4f0", "metadata": { "slideshow": { "slide_type": "-" }, "tags": [ "remove-cell" ] }, "source": [ "**CS1302 Introduction to Computer Programming**\n", "___" ] }, { "cell_type": "markdown", "id": "cb476fb0", "metadata": {}, "source": [ "[Sphinx](https://www.sphinx-doc.org/en/master/index.html) is a tool to generate high-quality documentations such as:\n", " - [Python](https://docs.python.org/3/)\n", " - [Numpy](https://numpy.org/doc/stable/)\n", " - [Pandas](https://pandas.pydata.org/docs/)" ] }, { "cell_type": "markdown", "id": "d5c14800", "metadata": {}, "source": [ "Sphinx provides an extension called [autodoc](https://www.sphinx-doc.org/en/master/usage/extensions/autodoc.html) that can automatically generate documentations from the docstrings of a module. We will use it to document our `recurtools` module used in Lecture 6." ] }, { "cell_type": "markdown", "id": "2c78b3e5", "metadata": {}, "source": [ "## Getting started" ] }, { "cell_type": "markdown", "id": "20c8b84c", "metadata": {}, "source": [ "We will run the sphinx in the terminal. To start a termial session in JupyterLab:\n", "\n", "- Open the Launcher (`File->New Launcher`).\n", "- Start a new termial session by clicking the `Terminal` icon under `Other`." ] }, { "cell_type": "markdown", "id": "994feae4", "metadata": {}, "source": [ "You should see the terminal tab with a prompt for your input:\n", "\n", "```\n", "(base) {username}@{hostname}:{cd}$ ▯\n", "```" ] }, { "cell_type": "markdown", "id": "d9ad1913", "metadata": {}, "source": [ "````{note}\n", "\n", "- `(base)` indicates the [conda environment](https://conda.io/projects/conda/en/latest/user-guide/getting-started.html#managing-environments) you are using.\n", "- `{username}` shows your username.\n", "- `{hostname}` shows the name of the server running your jupyter environment.\n", "- `{cd}` shows your current directory. By default, it shows `~`, which is an alias of your home directory `/home/{username}`.\n", "- ▯ is the cursor, where you can run a [`bash` command](https://en.wikipedia.org/wiki/Bash_(Unix_shell)).\n", "\n", "````" ] }, { "cell_type": "markdown", "id": "3130d54a", "metadata": {}, "source": [ "**How to configure sphinx?**" ] }, { "cell_type": "markdown", "id": "df76df2c", "metadata": { "tags": [] }, "source": [ "Run the following quick-start command in a terminal to create the configuration files in a folder called `docs` under your home directory:\n", "\n", "```Bash\n", "sphinx-quickstart ~/docs\n", "```" ] }, { "cell_type": "markdown", "id": "c0ceef33", "metadata": {}, "source": [ "````{tip}\n", "\n", "- You need to press enter to execute the command.\n", "- `~/docs` expands to `/home/{username}/docs`. \n", "- You can learn more about a command by running it with the option `--help` such as \n", " ```Bash\n", " sphinx-quickstart --help\n", " ```\n", "\n", "````" ] }, { "cell_type": "markdown", "id": "22b94649", "metadata": {}, "source": [ "You will be asked a few questions: \n", "- Answer `y` to the first question to use separate source and build directories.\n", "- Answer whatever you desire for the remaining questions." ] }, { "cell_type": "markdown", "id": "3ab11f1f", "metadata": {}, "source": [ "```\n", "You have two options for placing the build directory for Sphinx output.\n", "Either, you use a directory \"_build\" within the root path, or you separate\n", "\"source\" and \"build\" directories within the root path.\n", "> Separate source and build directories (y/n) [n]: y\n", "\n", "The project name will occur in several places in the built documentation.\n", "> Project name: Recurtools\n", "> Author name(s): CHAN Chung\n", "> Project release []: beta\n", "```" ] }, { "cell_type": "markdown", "id": "fd65e08a", "metadata": {}, "source": [ "````{note}\n", "\n", "- [Project release](https://www.sphinx-doc.org/en/master/usage/configuration.html#confval-release) specifies the full project version. See [software versioning](https://en.wikipedia.org/wiki/Software_versioning) for the convention.\n", "- If successful, the command will print the message\n", " ```\n", " Finished: An initial directory structure has been created.\n", " ```\n", "\n", "````" ] }, { "cell_type": "markdown", "id": "c0eeda89", "metadata": {}, "source": [ "**How to build the documentation?**" ] }, { "cell_type": "markdown", "id": "295ae414", "metadata": {}, "source": [ "Run the build script:\n", "\n", "```Bash\n", "sphinx-build -b html ~/docs/source ~/www/recurtools\n", "```" ] }, { "cell_type": "markdown", "id": "aa00e167", "metadata": {}, "source": [ "````{note}\n", "\n", "The command uses the html builder to generate static webpages to `~/docs/recurtools` based on the configuration from `~/docs/source`.\n", "\n", "````" ] }, { "cell_type": "markdown", "id": "2c0fb13b", "metadata": {}, "source": [ "**How to preview the documentation?**" ] }, { "cell_type": "markdown", "id": "a070fdf0", "metadata": {}, "source": [ "You can view the documentation by \n", "- clicking `File->New Launcher`, and\n", "- clicking the icon `www` and then folder `recurtools`." ] }, { "cell_type": "markdown", "id": "01d1ea6d", "metadata": {}, "source": [ "The documentation is currently empty because we have not specified the module to document." ] }, { "cell_type": "markdown", "id": "c10a352b", "metadata": {}, "source": [ "## Autodoc" ] }, { "cell_type": "markdown", "id": "cc216f61", "metadata": {}, "source": [ "**How to configure sphinx to document a module automatically from its docstrings?**" ] }, { "cell_type": "markdown", "id": "4309d673", "metadata": {}, "source": [ "From the `File Browser` tab, navigate to the `docs/source` folder under your home directory and open `conf.py` by double clicking it and modify it as follows. A sample can be found in `cs1302/Lab6/conf.py`." ] }, { "cell_type": "markdown", "id": "4556440d", "metadata": {}, "source": [ "**Path setup**" ] }, { "cell_type": "markdown", "id": "ad2d2e4e", "metadata": { "tags": [] }, "source": [ "Uncomment and modify the relevant lines as follows to add the module path to the system path: \n", "```Python\n", "import os\n", "import sys\n", "sys.path.insert(0, os.path.expanduser('~/cs1302/Lecture6'))\n", "```" ] }, { "cell_type": "markdown", "id": "e2dbe853", "metadata": {}, "source": [ "````{note}\n", "\n", "- The module path `~/cs1302/Lecture6` contains the `recurtools` module. \n", "- The module path is searched first as it is added to the beginning of the system path.\n", "\n", "````" ] }, { "cell_type": "markdown", "id": "d8afe502", "metadata": {}, "source": [ "**General configuration**" ] }, { "cell_type": "markdown", "id": "5f2c72cd", "metadata": {}, "source": [ "Add the necessary extensions as follows to `extensions`:\n", "```Python\n", "extensions = ['sphinx.ext.autodoc', 'sphinx.ext.napoleon']\n", "```" ] }, { "cell_type": "markdown", "id": "f57472a3", "metadata": {}, "source": [ "````{note}\n", "\n", "- [`sphinx.ext.autodoc`](https://www.sphinx-doc.org/en/master/usage/extensions/autodoc.html) generates documentation from docstrings in [reStructuredText format (rst)](https://www.sphinx-doc.org/en/master/usage/restructuredtext/basics.html) format, which is powerful but makes the docstrings difficult to read.\n", "- [`sphinx.ext.napoleon`](https://www.sphinx-doc.org/en/master/usage/extensions/napoleon.html) converts the more readable Numpy-style and Google-style docstrings to rst.\n", "\n", "````" ] }, { "cell_type": "markdown", "id": "fd8865ba", "metadata": {}, "source": [ "Change [`exclude_patterns`](https://nbsphinx.readthedocs.io/en/0.5.0/usage.html#exclude_patterns) to exclude temporary files in the hidden `.ipynb_checkpoints` folder: \n", "```Bash\n", "exclude_patterns = ['**.ipynb_checkpoints']\n", "```" ] }, { "cell_type": "markdown", "id": "0e39de29", "metadata": {}, "source": [ "````{note}\n", "\n", "`.ipynb_checkpoints` keep a backup of your files so you may recover them. However, `sphinx` will build documentation on those backup files unless we exclude them explicitly. \n", "\n", "````" ] }, { "cell_type": "markdown", "id": "96f5e5a8", "metadata": {}, "source": [ "**How to generate the documentation from docstrings?**" ] }, { "cell_type": "markdown", "id": "fbad7697", "metadata": {}, "source": [ "Run API documentation command to create the rst files for `recurtools`: \n", "```Bash\n", "sphinx-apidoc -f -o ~/docs/source ~/cs1302/Lecture6\n", "```" ] }, { "cell_type": "markdown", "id": "fcafa0c1", "metadata": {}, "source": [ "````{note}\n", "\n", "The above creates `modules.rst` and `recurtools.rst` under `~/docs/source`. In particular, `modules.rst` points to `recurtools.rst` as follows:\n", "\n", "```Markdown\n", "Lecture6\n", "========\n", "\n", ".. toctree::\n", " :maxdepth: 4\n", "\n", " recurtools\n", "```\n", "\n", "````" ] }, { "cell_type": "markdown", "id": "61e54eb0", "metadata": {}, "source": [ "Modify `index.rst` to point to `modules.rst` as follows: \n", "```Markdown\n", ".. Recurtools documentation master file, created by\n", " sphinx-quickstart on Sun Oct 31 11:51:38 2021.\n", " You can adapt this file completely to your liking, but it should at least\n", " contain the root `toctree` directive.\n", "\n", "Welcome to Recurtools's documentation!\n", "======================================\n", "\n", ".. toctree::\n", " :maxdepth: 2\n", " :caption: Contents:\n", "\n", " modules\n", "\n", "Indices and tables\n", "==================\n", "\n", "* :ref:`genindex`\n", "* :ref:`modindex`\n", "* :ref:`search`\n", "```" ] }, { "cell_type": "markdown", "id": "13aa1a2c", "metadata": {}, "source": [ "````{tip}\n", "\n", "- Note that there is no need to add the extension `.rst` as it is the default.\n", "- `modules` is the content of the directive `toctree`. It must have the same indentation as the arguments `:maxdepth:` and `:caption:` above and must be separated by a blank line.\n", "\n", "````" ] }, { "cell_type": "markdown", "id": "c5270de6", "metadata": {}, "source": [ "Rebuild the documentation with \n", "```Bash\n", "sphinx-build -b html ~/docs/source ~/www/recurtools\n", "```" ] }, { "cell_type": "markdown", "id": "2753071b", "metadata": {}, "source": [ "Preview the documentation again by refreshing or relaunching the `www` page." ] }, { "cell_type": "markdown", "id": "6a16b63d", "metadata": {}, "source": [ "**Exercise** (optional) \n", "\n", "Create a module `combinatorics` for the functions in Lab 6 and document them together with `recurtools` in Lecture 6." ] } ], "metadata": { "jupytext": { "text_representation": { "extension": ".md", "format_name": "myst", "format_version": 0.13, "jupytext_version": "1.11.5" } }, "kernelspec": { "display_name": "Python 3 (ipykernel)", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.8.8" }, "source_map": [ 12, 16, 21, 28, 32, 36, 43, 51, 63, 67, 75, 88, 94, 108, 120, 124, 132, 140, 144, 150, 154, 158, 162, 166, 170, 179, 188, 192, 199, 208, 215, 223, 227, 234, 252, 278, 287, 294, 298 ] }, "nbformat": 4, "nbformat_minor": 5 }