panoptipy

⚠️ Under development; use not currently recommended

A Package for the Static Code Quality Assessment of Python codebases. It scans local codebases or remote GitHub repositories and generates a report summarising various code quality metrics.

SVG logo of panoptipy

PyPI Status Python Version License Read the documentation at https://aeturrell.github.io/panoptipy/ Tests Codecov pre-commit Ruff Downloads Source

Linux macOS Windows

Quickstart

The main way to use panoptipy is through its command-line interface. Here’s how to scan a Python codebase that is in the “project” directory:

# Basic scan with default settings
$ panoptipy scan /path/to/project

To run on multiple directories, you can specify them as a space-separated list:

# Scan multiple directories
$ panoptipy scan /path/to/project1 /path/to/project2

You can also use wildcards to specify directories:

# Scan all directories in the current directory
$ panoptipy scan ./*

Using the scan command in this way will:

  • Load all configured checks (there’s a list below)
  • Analyse your codebase
  • Generate a report with the results
  • Output the report to the console (by default)

The scan report shows:

  • Overall codebase rating (Gold, Silver, Bronze, or Problematic)
  • A summary of whether each individual check passed or not
  • Detailed information about any failures

What is panoptipy for?

There is a lot of overlap between panoptipy and pre-commit (with the relevant hooks). So what are the differences?

  • pre-commit is meant to be used by developers to check their own code before they commit it or in Continuous Integration (CI) / Continous Deployment (CD) pipelines.
  • panoptipy has features that help the leaders and managers of other developers. To that end it can summarise the results of many code repos at once, eg:
    • all those written by a (GitHub) team
    • all those by a specific (GitHub) user
  • panoptipy can be be used to generate and export reports in a variety of formats (JSON, parquet) for further analysis.

These packages are similar in that they can both be used in CI/CD pipelines but pre-commit should be your first port of call for that and is not only more geared to that use, but also far more mature.

Installation

You can use panoptipy as a stand-alone tool via Astral’s uv package:

uvx panoptipy scan .

Alternatively, you can install it as a Python package with pip install or uv add.

To install the development version from git, use:

pip install git+https://github.com/aeturrell/panoptipy.git

Documentation

You can find the full documentation for panoptipy at https://aeturrell.github.io/panoptipy/.

GitHub integration

panoptipy can be used to scan multiple GitHub repositories. This is useful for people or organisations that want to assess the quality of their codebases.

Note that, even for scanning public repos, you will need a GitHub token. You can find out more about authenticating with the GitHub GraphQL API here.

The two commands that run against multiple GitHub repositories are scan-user and scan-team.

Here’s how to use them:

# Scan all repos by a given GitHub user
panoptipy scan-user USERNAME --token YOUR_GITHUB_TOKEN
# Scan all repos by a given GitHub team
panoptipy scan-team ORGANISATION_NAME TEAM_NAME --token YOUR_GITHUB_TOKEN

You can also limit the repositories that are scanned by using the --max-repos option. This is useful if you want to test the tool on a small number of repositories before running it on all of them.

# Scan all repos by a given GitHub user but limit to only retrieving the fist 5 repos
panoptipy scan-user USERNAME --max-repos 5 --token YOUR_GITHUB_TOKEN

Options

Configuration

# Scan with custom configuration file
panoptipy scan /path/to/project --config path/to/config.toml

If you wish to configure panoptipy to your needs, you can do so by passing a TOML file with the --config option. Here’s an example of a configuration file in TOML:

[tool.panoptipy]
checks = { enabled = ["large_files", "ruff_linting"], disabled = [], critical = ["ruff_linting"] }

[tool.panoptipy.thresholds]
max_file_size = 1000
min_readme_length = 200

Note that critical checks are ones that cause CI/CD pipelines to fail. The CLI will:

  • Exit with code 1 if any critical checks failed
  • Exit with code 0 if no critical checks failed

Command line output options

Although the default output is to the console, you can also specify some other options. The currently supported output formats are:

['console', 'json', 'parquet', 'svg', 'html']

For example, to use the json format, you can run:

panoptipy scan /path/to/project --format json

Or for parquet, you can run:

panoptipy scan /path/to/project --format parquet --output /path/to/output.parquet

Note that while the --output argument is optional for json, it is required for parquet.

Example Use on This Repo

panoptipy scan .

Repository: ..


╭────────────────────────────── Panoptipy Report ──────────────────────────────╮
│ Codebase Rating: SILVER                                                      │
╰──────────────────────────────────────────────────────────────────────────────╯

Summary:
Total checks: 10
Fail: 2
Pass: 8
Pass rate: 80.0%
                                                                                
                              Check Results for ..                              
╭──────────┬─────────────────┬─────────────────────────────────────────────────╮
│  Status  │ Check ID        │ Message                                         │
├──────────┼─────────────────┼─────────────────────────────────────────────────┤
│ ❌       │ docstrings      │ Found 35 public items without docstrings        │
│ ❌       │ private_key     │ Found 1 files containing private keys           │
│ ✅       │ ruff_linting    │ No linting issues found                         │
│ ✅       │ ruff_format     │ All files are formatted                         │
│ ✅       │ large_files     │ No version-controlled files exceed size         │
│          │                 │ threshold (500KB)                               │
│ ✅       │ notebook_output │ All notebooks are stripped of outputs and       │
│          │                 │ excess metadata                                 │
│ ✅       │ pydoclint       │ All docstrings match type signatures in 16      │
│          │                 │ files                                           │
│ ✅       │ pyproject_toml… │ pyproject.toml validated successfully by        │
│          │                 │ validate-pyproject API.                         │
│ ✅       │ has_tests       │ Found 8 tests in the codebase                   │
│ ✅       │ readme          │ README exists with sufficient content           │
╰──────────┴─────────────────┴─────────────────────────────────────────────────╯

Details:
╭───────────────────────────────── docstrings ─────────────────────────────────╮
│ missing_docstrings:                                                          │
│   • src/panoptipy/checks.py:get_tracked_files                                │
│   • src/panoptipy/checks.py:safe_check_run                                   │
│   • src/panoptipy/checks.py:parse_tool_output                                │
│   • src/panoptipy/checks.py:success_result                                   │
│   • src/panoptipy/checks.py:fail_result                                      │
│   • src/panoptipy/checks.py:NotebookOutputCheck                              │
│   • src/panoptipy/checks.py:category                                         │
│   • src/panoptipy/checks.py:run                                              │
│   • src/panoptipy/checks.py:category                                         │
│   • src/panoptipy/checks.py:run                                              │
│   ... and 25 more                                                            │
╰──────────────────────────────────────────────────────────────────────────────╯
╭──────────────────────────────── private_key ─────────────────────────────────╮
│ files_with_private_keys:                                                     │
│   • {'file': 'src/panoptipy/checks.py', 'pattern': 'BEGIN RSA PRIVATE KEY',  │
│ 'message': 'Contains private key pattern: BEGIN RSA PRIVATE KEY'}            │
│ count: 1                                                                     │
╰──────────────────────────────────────────────────────────────────────────────╯

Checks

There are several different available checks that can be run. These are:

check_id description
docstrings Checks that public functions and classes have docstrings (excluding tests)
ruff_linting Checks code for linting errors using ruff
ruff_format Checks that code follows proper formatting using ruff format
private_key Checks for private keys in version-controlled files
large_files Checks for large files that exceed size threshold
notebook_output Checks that Jupyter notebooks don't contain output cells or unnecessary metadata
pydoclint Checks that docstrings match type signatures using pydoclint
pyproject_toml_validate Checks pyproject.toml format and schema using validate-pyproject API
has_tests Checks if tests are present in the codebase using AST parsing
readme Checks for the existence and content of a README file

You can find more information about each check in the reference documentation.

Requirements

You can find a full list of requirements in the pyproject.toml file.

License

Distributed under the terms of the MIT license, panoptipy is free and open source software.

Issues

If you encounter any problems, please file an issue along with a detailed description.