| name | python-packaging |
| description | Create and publish distributable scientific Python packages following Scientific Python community best practices. Covers pyproject.toml, src layout, Hatchling, metadata, CLI entry points, and PyPI publishing. |
| metadata | {"assets":["assets/pyproject-minimal.toml","assets/pyproject-full-featured.toml","assets/readme-template.md","assets/github-actions-publish.yml","assets/sphinx-conf.py","assets/.gitignore"],"references":["references/common-issues.md","references/docstrings.md","references/metadata.md","references/patterns.md"],"scripts":["scripts/cli-example.py"]} |
Scientific Python Packaging
A comprehensive guide to creating, structuring, and distributing Python packages for scientific computing, following the Scientific Python Community guidelines. This skill focuses on modern packaging standards using pyproject.toml, PEP 621 metadata, and the Hatchling build backend.
Quick Decision Tree
Package Structure Selection:
START
├─ Pure Python scientific package (most common) → Pattern 1 (src/ layout)
├─ Need data files with package → Pattern 2 (data/ subdirectory)
├─ CLI tool → Pattern 5 (add [project.scripts])
└─ Complex multi-feature package → Pattern 3 (full-featured)
Build Backend Choice:
START → Use Hatchling (recommended for scientific Python)
├─ Need VCS versioning? → Add hatch-vcs plugin
├─ Simple manual versioning? → version = "X.Y.Z" in pyproject.toml
└─ Dynamic from __init__.py? → [tool.hatch.version] path
Dependency Management:
START
├─ Runtime dependencies → [project] dependencies
├─ Optional features → [project.optional-dependencies]
├─ Development tools → [dependency-groups] (PEP 735)
└─ Version constraints → Use >= for minimum, avoid upper caps
Publishing Workflow:
1. Build: python -m build
2. Check: twine check dist/*
3. Test: twine upload --repository testpypi dist/*
4. Verify: pip install --index-url https://test.pypi.org/simple/ pkg
5. Publish: twine upload dist/*
Common Task Quick Reference:
mkdir -p my-pkg/src/my_pkg && cd my-pkg
pip install -e . --group dev
python -m build
pip install dist/*.whl
twine upload dist/*
When to Use This Skill
- Creating scientific Python libraries for distribution
- Building research software packages with proper structure
- Publishing scientific packages to PyPI
- Setting up reproducible scientific Python projects
- Creating installable packages with scientific dependencies
- Implementing command-line tools for scientific workflows
- Following community standards for scientific Python development
- Preparing packages for peer review and publication
Core Concepts
1. Modern Build Systems
Python packages now use standardized build systems instead of classic setup.py:
- PEP 621: Standardized project metadata in
pyproject.toml
- PEP 517/518: Build system independence
- Build backend: Hatchling
- No classic files: No
setup.py, setup.cfg, or MANIFEST.in
2. Build Backend: Hatchling
- Hatchling: Excellent balance of speed, configurability, and extendability
- Modern, standards-compliant build backend
- Automatic package discovery in
src/ layout
- VCS-aware file inclusion for SDists
- Extensible through plugins
3. Package Structure
- src/ layout: Required for proper isolation (prevents importing uninstalled code)
- Automatic discovery: Hatchling auto-detects packages in
src/
- Standard structure: Consistent organization for testing and documentation
4. Scientific Python Standards
- Dependency management: Careful version constraints
- Python version support: Minimum version without upper caps
- Development dependencies: Use dependency-groups (PEP 735)
- Documentation: Include README, LICENSE, and docs folder
- Testing: Dedicated tests folder
Quick Start
Minimal Scientific Package Structure
my-sci-package/
├── pyproject.toml
├── README.md
├── LICENSE
├── src/
│ └── my_sci_package/
│ ├── __init__.py
│ ├── analysis.py
│ └── utils.py
├── tests/
│ ├── test_analysis.py
│ └── test_utils.py
└── docs/
└── index.md
See assets/pyproject-minimal.toml for a complete minimal pyproject.toml template.
Package Structure Patterns
See references/patterns.md for detailed package structure patterns including:
- Pure Python scientific package (recommended)
- Scientific package with data files
- Versioning strategies
- Building and publishing workflows
- Testing installation
Project Metadata
See references/metadata.md for detailed information on:
- License configuration (SPDX format)
- Python version requirements
- Dependency management
- Classifiers
- Optional dependencies (extras)
- Development dependencies (dependency groups)
Command-Line Interface
For CLI tool implementation, see scripts/cli-example.py for a complete example using Click.
Register in pyproject.toml:
[project.scripts]
sci-analyze = "my_sci_package.cli:main"
File Templates
Ready-to-use templates are available in the assets/ directory:
Documentation
NumPy-style Docstrings
See references/docstrings.md for examples of NumPy-style docstrings and documentation best practices.
Checklist for Publishing Scientific Packages
Best Practices for Scientific Python Packages
- Use src/ layout - Prevents importing uninstalled code, ensures proper testing
- Use pyproject.toml - Modern standard, tool-independent configuration
- Use Hatchling - Modern, fast, and configurable build backend
- No classic files - Avoid setup.py, setup.cfg, MANIFEST.in
- Version constraints - Minimum versions for dependencies, no upper cap for Python
- Test SDist contents - Always verify what files are included/excluded
- Use TestPyPI - Always test publishing before going to production
- Document thoroughly - README, docstrings, Sphinx documentation
- Include LICENSE - Use SPDX identifiers, choose appropriate scientific license
- Use dependency-groups - For development dependencies (PEP 735)
- Semantic versioning - Clear versioning strategy
- Automate CI/CD - GitHub Actions for testing and publishing
- Type hints - Include py.typed marker for typed packages
- Citation information - Make it easy for users to cite your work
- Community standards - Follow Scientific Python guidelines
Common Issues and Solutions
See references/common-issues.md for solutions to:
- Import errors in tests
- Missing files in distribution
- Dependency conflicts
- Python version incompatibility
Resources