Sort class methods and module-level functions into configurable, regex-matched groups
Project description
funcsort
A Python tool that automatically sorts class methods and module-level functions into configurable, regex-matched groups.
funcsort ships with a default configuration that reproduces its classic behaviour — sorting class methods by visibility (creational → dunder → public → protected → private) and type (instance → class → static) — but the engine underneath is fully generic: you define your own ordered groups, match member names with regular expressions, and control sorting at both class and module scope.
Features
- Generic, configuration-driven engine with a behaviour-preserving default
- Dependency-safe: never moves a definition above code that reads it at import time
- Define your own groups and ordering; match member names with regex
- Sort both class methods and module-level functions
- Optionally sort module-level assignments/constants by opting a group into them
- Per-group filters by member kind, method type and scope
- Configurable via a dedicated
funcsort.tomlor[tool.funcsort]inpyproject.toml - Pre-commit hook integration, colored output, check mode (CI) and diff mode
Installation
# Using uv (recommended)
uv add funcsort
# Using pip
pip install funcsort
# For development
git clone https://github.com/HEROgold/funcsort
cd funcsort
uv sync
Configuration
funcsort reads configuration from a dedicated funcsort.toml if present, otherwise
from the [tool.funcsort] table of pyproject.toml. Both use the same [tool.funcsort]
section and keys.
[tool.funcsort]
# Method type ordering within each group (secondary sort, optional)
# Options: "instance", "class", "static" Default: ["instance", "class", "static"]
method_type_order = ["instance", "class", "static"]
# Sort module-level functions too (default: true)
sort_module = true
# Avoids moving definitions that could raise NameErrors or break code dependencies
# (default: true). See the docs on dependency safety:
# https://herogold.github.io/funcsort/dependency-safety/
respect_dependencies = true
# Exclude files/directories matching these glob patterns (optional)
# exclude = ["tests/*", "migrations/*.py"]
With no configuration, funcsort uses its built-in default groups. For full control,
define an ordered list of [[tool.funcsort.groups]]; this replaces the built-in
groups entirely, and the list order is the output order:
# Sort module-level UPPER_CASE constants to the very top.
[[tool.funcsort.groups]]
name = "constants"
match = "^[A-Z][A-Z0-9_]*$"
kind = ["assignment"] # opt this group into assignments
scope = "module" # only at module scope
# Catch-all so nothing is ever "unmatched".
[[tool.funcsort.groups]]
name = "everything_else"
match = ".*"
Every key, the built-in default groups and the per-group filters are documented under Configuration.
Usage
# Sort a single file, several files, or a directory (recursive by default)
funcsort example.py
funcsort file1.py file2.py
funcsort src/
# Non-recursive directory sorting
funcsort src/ --no-recursive
# Check if files need sorting (useful for CI), and show a diff
funcsort --check src/
funcsort --diff example.py
# Sort class methods only, leaving module-level functions untouched
funcsort --no-sort-module src/
# Sort by group order alone, ignoring load-time dependencies (can break imports)
funcsort --no-respect-dependencies src/
# Exclude specific files or directories
funcsort --exclude "tests/*" --exclude "migrations/*.py" src/
Note: By default, funcsort excludes all dot-prefixed directories (e.g. .venv,
.git, .pytest_cache) and common build directories (venv, __pycache__,
node_modules) when scanning directories recursively. You can add custom exclusions via
CLI flags or the config file.
Individual files, classes and members can opt out of sorting with a # nosort comment —
see Skipping sorting.
Pre-commit Integration
Add to your .pre-commit-config.yaml:
repos:
- repo: local
hooks:
- id: funcsort
name: funcsort
entry: funcsort
language: python
types: [python]
additional_dependencies: ["funcsort"]
Then install the hook:
pip install pre-commit
pre-commit install
Documentation
- Configuration — every key, the default groups, and the per-group filters
- Sorting behaviour — the two-level sort and the minimise-movement rule
- Dependency safety — why a definition is never moved below code that reads it at import time
- Skipping sorting — the
# nosortescape hatches - Example — a class before and after sorting
- API Reference — the public Python API
Development
# Install dependencies
uv sync
# Run on example file
uv run funcsort example.py
# Test with check mode
uv run funcsort --check example.py
# View diff
uv run funcsort --diff example.py
# Build the documentation site locally
uv run --group docs mkdocs serve
License
MIT
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file funcsort-1.0.0.tar.gz.
File metadata
- Download URL: funcsort-1.0.0.tar.gz
- Upload date:
- Size: 135.7 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: uv/0.12.1 {"installer":{"name":"uv","version":"0.12.1","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
c99fd6443b0cc5855fce115a60e969cbd8042f2fdbc2470b15e994e0aa36d21c
|
|
| MD5 |
e7f3a71507c203fcce4d290f8f2de503
|
|
| BLAKE2b-256 |
f3f170a2aff097e730dc6b6988632c74c3bb2f0abef631ed7c9738225142de36
|
File details
Details for the file funcsort-1.0.0-py3-none-any.whl.
File metadata
- Download URL: funcsort-1.0.0-py3-none-any.whl
- Upload date:
- Size: 28.1 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: uv/0.12.1 {"installer":{"name":"uv","version":"0.12.1","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b4533374f2c5b60eb41093cdd43d47b9dd9c704b76708995542eb9c91c22bbbc
|
|
| MD5 |
1ac03a6393313fd1dff28603cb453bd4
|
|
| BLAKE2b-256 |
b2507e25e949e9fc7e4fedc689013d8389b1227f5fd3376a352893144cd6de9c
|