Library / SDK
econchick/interrogate avatar
econchick/interrogate

interrogate: measuring docstring coverage in a Python codebase

Explain yourself! Interrogate a codebase for docstring coverage.

676 stars57 forksPythonMIT

At a glance

What is it?
interrogate is a Python command line tool that reports which modules, classes, functions and methods carry docstrings and which do not, and fails a build when coverage drops below a threshold. It is a small, configurable linter for one specific kind of documentation debt, and it treats the docstring as a metric rather than as prose.
Who is it for?
interrogate suits a team that wants a hard, measurable floor on docstrings rather than a style guide nobody enforces, because it turns documentation coverage into a number a CI job can fail on, and the per-file table tells you which module to open first.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 17 days ago.
What is it written in?
Mainly Python, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.

Editorial analysis

A coverage metric for docstrings, not a style checker

The README's summary line is the whole pitch: interrogate a codebase for docstring coverage. The tool checks your code base for missing docstrings, and it reports which methods, functions, classes and modules have docstrings and which do not. The justification given is that documentation should be as important as code itself, and that it should live within code, pointing at standardized Python docstrings under PEP 257, which allow developers to navigate libraries as simply as calling help() on objects, and work with tools like Sphinx, pydoc and Docutils to generate HTML, LaTeX, PDFs and so on. Three uses are named. You can get an understanding of how well your code is documented, you can add it to CI/CD checks to enforce documentation on newly-added code, and you can assess a new code base for one aspect of code quality and maintainability. The third of those is the one that makes this a migration tool rather than a lint rule, because the interesting question on an inherited codebase is not whether the newest file is documented but where the missing docstrings are concentrated.

Installation, and the optional PNG badge dependency chain

The package is on PyPI and on GitHub, and the recommended installation method is pip-installing into a virtualenv:

bash
    $ pip install interrogate

There is one extra worth understanding before you add it to a build. interrogate provides a way to generate a shields.io-like coverage badge as an SVG file, and to generate a PNG file instead you install interrogate with the extras [png]:

bash
    $ pip install interrogate[png]

The notice attached to that is that additional system libraries or tools may be required to generate a PNG file of the coverage badge. On Windows you need to install the Visual C++ compiler for Cairo, on macOS you need cairo and libffi, and on Linux the cairo, python3-dev and libffi-dev packages, with names varying by distribution. The README refers to the cairosvg documentation for more on this. The macOS case has its own known failure mode, where an error like OSError: no library called cairo-2 was found, and the suggested fix is to export DYLD_FALLBACK_LIBRARY_PATH=/opt/homebrew/lib and rerun the command. The SVG path has no such dependency, which is the reason to prefer it unless something in your pipeline insists on a raster badge.

Running it on a project, and what the pass threshold means

The tool takes a path and reports a result against a minimum:

bash
    $ interrogate [PATH]
    RESULT: PASSED (minimum: 80.0%, actual: 100.0%)

The example output reports against a minimum of 80 percent, and a fail-under threshold makes interrogate exit non-zero when coverage falls below it and can be dropped straight into a CI job as an enforcement step rather than a report. Adding verbosity gives a per-file summary table:

bash
    $ interrogate -v [PATH]

and the table is where the tool earns its keep, because it breaks the total down by file with a total, a miss count, a cover count and a percentage per file, ending with a TOTAL row. The README shows a run over a project of its own, with src/interrogate files such as __init__.py, __main__.py, badge_gen.py, cli.py, config.py, coverage.py and utils.py alongside the tests directory, all at 100 percent in the example. A second level of verbosity, interrogate -vv, switches the table to a detailed per-symbol view that names each function or method with its line number and marks it COVERED, which is the form you want when you are working through a backlog of missing docstrings one file at a time.

The configuration block is where the real decisions live

interrogate is configurable through its own section in pyproject.toml, and the project's configuration for itself is a good model to copy. The defaults are strict. ignore-init-method is true but ignore-init-module, ignore-magic, ignore-semiprivate, ignore-private, ignore-module and ignore-property-decorators are all false, which means dunder methods, semi-private and private members, module docstrings and property decorators all count against you unless you say otherwise. fail-under is 95, exclude lists tests/functional/sample, setup.py and docs, verbose is 0, omit-covered-files is false, quiet is false, whitelist-regex and ignore-regex are empty lists, and color is true. Two of those are worth attention in particular. A whitelist-regex and an ignore-regex give you a way to exempt code that should not be documented, and an exclude list lets you drop whole paths from the measurement, which is how a project keeps its own configuration file and documentation tree from inflating its own number. The project also sets up mypy in strict mode with pretty output and ignore_missing_imports enabled, black at a line length of 79, isort with two lines after imports and known_first_party set to interrogate, and a coverage configuration with fail_under = 95 and branch coverage enabled.

An auditable tool, and a clue to how it is trusted

The repository itself is evidence about the tool. It runs interrogate on its own codebase through the [tool.interrogate] section, with a fail-under of 95, so the project is held to the standard it asks of others. The packaging is done with setuptools, and setup.py reads the version and other metadata out of src/interrogate/__init__.py with a regular expression, and the find_packages call uses a where argument of src, so the package lives in a src layout. The wheel content check in pyproject.toml restricts the toplevel to interrogate alone, which keeps the installed package clean. The test suite is configured with addopts of -ra, --strict-markers and --strict-config, testpaths set to tests, and xfail_strict enabled, so a test that is expected to fail and then passes is itself an error. On the tooling side, the repository carries a .pre-commit-config.yaml and a .pre-commit-hooks.yaml, which is the pattern for exposing a linter to teams that prefer to run everything on commit, a tox.ini for multi-environment runs, a codecov.yml, a MANIFEST.in, and a .readthedocs.yaml for the documentation build. The README also links a coverage badge in the documentation style and a testing coverage badge from codecov, so the project's own docstring coverage is visible in its README.

What a docstring percentage does not tell you

The limitation of this tool is the limitation of every coverage metric applied to prose. interrogate can tell you that a function has a docstring; it cannot tell you whether the docstring is correct, whether the parameter descriptions match the signature, or whether the docstring says anything the name does not already say. A codebase can reach 100 percent and still be worse documented than one at 60, because the missing docstrings at 60 may be the only interesting ones. A second limit is the scope of what counts as documentation. interrogate counts docstrings and nothing else, so a project that documents its public API in a separate reference site, in type hints, or in a long module-level design note will score badly while being perfectly well documented. The third limit is that the number is only as useful as the threshold you set, and a threshold that is too high for a legacy codebase turns the tool into a source of noise that teams learn to ignore. The tool's own configuration shows how to handle that, with exclude lists and regex options, but the setting is yours to make and to defend.

The tool that changed the author's mind about docstrings

There is a story here that explains the project. The README is written in the first person, and the opening claim is that documentation should be as important as code itself and should live within code. The author is Lynn Root, whose name appears in the copyright header of setup.py and in the paths of the example runs. The project carries a badge in the README of a pink sloth logo, and the tool's own tagline is explain yourself, which is a framing that treats an undocumented function as something the function is failing to do rather than something the writer forgot to do. The distribution has one tagged release, 1.7.0 on 2024-04-07, and the last push to the repository was on 2026-10-06, so the code is moving while the release tags are old, which is worth knowing if you pin a version. The documentation is published on readthedocs, the project is MIT licensed, it supports Python 3.8 and above, and the topics attached to the repository are code-quality, coverage, documentation, hacktoberfest and python.

Editorial conclusion

interrogate suits a team that wants a hard, measurable floor on docstrings rather than a style guide nobody enforces, because it turns documentation coverage into a number a CI job can fail on, and the per-file table tells you which module to open first. It is the wrong tool if your project documents its public API through a separate reference site rather than docstrings, since interrogate counts docstrings and nothing else, and it is the wrong tool for a codebase where private helpers are deliberately left undocumented, unless you are prepared to tune the ignore flags it provides. Verify first which categories you want counted, since the defaults in the project's own configuration are strict and the ignore options are the difference between a useful signal and a wall of failures, and note that the newest release is 1.7.0 from 2024-04-07 while the last push to the repository was on 2026-10-06.

Frequently asked questions

How do I install interrogate?

It is available on PyPI and GitHub, and the recommended method is pip install interrogate inside a virtualenv. If you want to generate a PNG badge rather than SVG, install it with the extras as pip install interrogate[png], which also needs system libraries such as cairo and libffi.

How do I see which files are missing docstrings?

Run interrogate with the -v flag for a per-file summary table listing total, miss, cover and coverage percentage for each file, and with -vv for a detailed view that names each function or method with its line number and whether it is COVERED.

Can I make interrogate fail the build when coverage drops?

Yes. The tool compares against a minimum and the README's example output shows RESULT: PASSED (minimum: 80.0%, actual: 100.0%). Setting fail-under in the [tool.interrogate] section of pyproject.toml sets the threshold, and the README lists adding it to CI/CD checks to enforce documentation on newly-added code.

Can I exclude private methods and modules from the count?

Yes. The configuration options include ignore-init-method, ignore-init-module, ignore-magic, ignore-semiprivate, ignore-private, ignore-module and ignore-property-decorators, plus an exclude list of paths, a whitelist-regex and an ignore-regex for exemptions by pattern.

What Python versions does interrogate support?

The README states that interrogate supports Python 3.8 and above, and the package classifiers list Python 3.8 through 3.10.

Official sources

  1. econchick/interrogate on GitHub
  2. License: MIT
  3. Project website
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/econchick-interrogate.svg)](https://hysenlabs.com/projects/econchick-interrogate)

Was this useful?