Developer Guide#

This page describes how to contribute to g4hunterpy3, including setting up a development environment, running tests, writing code, and submitting changes.

Setting Up a Development Environment#

  1. Fork and clone the repository:

    git clone https://github.com/holehouse-lab/g4hunterpy3.git
    cd g4hunterpy3
    
  2. Create a conda environment for development:

    conda create -n g4hunter-dev python=3.11 -y
    conda activate g4hunter-dev
    
  3. Install the package in editable mode with test dependencies:

    pip install -e ".[test]"
    
  4. Verify everything is working:

    pytest
    

Project Layout#

g4hunterpy3/
├── g4hunterpy3/            # main package
│   ├── __init__.py
│   ├── core.py             # scoring algorithms
│   ├── plotting.py         # visualization functions
│   ├── scripts/
│   │   └── cli.py          # command-line interface
│   └── tests/
│       ├── test_core.py
│       ├── test_plotting.py
│       └── test_g4hunterpy3.py
├── docs/                   # Sphinx documentation
├── pyproject.toml          # build config & dependencies
└── setup.cfg               # flake8 / coverage settings

Development Workflow#

  1. Create a feature branch from main:

    git checkout -b feature/my-new-feature
    
  2. Make your changes, keeping commits small and focused.

  3. Run the test suite before committing:

    pytest
    
  4. Push your branch and open a Pull Request against main.

Running Tests#

The test suite uses pytest:

# run all tests
pytest

# run with verbose output
pytest -v

# run a specific test file
pytest g4hunterpy3/tests/test_core.py

# run a single test by name
pytest -k "test_base_scores"

# run with coverage report
pytest --cov=g4hunterpy3

Writing Code#

Style guidelines#

  • Follow PEP 8 for Python style.

  • Maximum line length is 119 characters (configured in setup.cfg).

  • Use NumPy-style docstrings for all public functions and classes.

Docstring example#

def my_function(seq: str, window_size: int = 25) -> np.ndarray:
    """Short one-line summary of the function.

    Longer description if needed, explaining the algorithm or
    important behavior.

    Parameters
    ----------
    seq : str
        Input DNA sequence.
    window_size : int, default=25
        Sliding window length in bases.

    Returns
    -------
    numpy.ndarray
        Description of the return value.

    Raises
    ------
    ValueError
        If window_size is invalid.
    """

Type hints#

  • Add type hints to function signatures.

  • The codebase uses from __future__ import annotations for forward references.

Writing Tests#

  • Place test files in g4hunterpy3/tests/.

  • Name test files test_<module>.py and test functions test_<thing>().

  • Test both normal behavior and edge cases.

  • Keep tests fast and independent of external resources.

Example:

import numpy as np
from g4hunterpy3.core import base_scores

def test_base_scores_g_run():
    """G-runs should produce positive scores capped at 4."""
    scores = base_scores("GGGGG")
    assert (scores == 4).all()

def test_base_scores_mixed():
    """Non-G/C bases should score 0."""
    scores = base_scores("ATATA")
    assert (scores == 0).all()

Building the Documentation#

The docs use Sphinx with the pydata-sphinx-theme. To build locally:

# install doc dependencies
pip install -r docs/requirements.txt

# build HTML docs
cd docs
make html

# open in browser
open _build/html/index.html    # macOS
xdg-open _build/html/index.html  # Linux

When adding new public functions or modules, make sure they appear in docs/api.rst so they are included in the API reference.

Pull Request Checklist#

Before submitting a PR, please verify:

  • [ ] All existing tests pass (pytest).

  • [ ] New functionality includes tests.

  • [ ] Public functions have NumPy-style docstrings.

  • [ ] Code follows the style guidelines (PEP 8, 119-char line limit).

  • [ ] Documentation builds without warnings (make html in docs/).

  • [ ] Commit messages are clear and descriptive.

Reporting Issues#

If you find a bug or have a feature request, please open an issue on GitHub. Include:

  • A description of the problem or desired feature.

  • Steps to reproduce (for bugs).

  • Your Python version and OS.

  • The output of python -c "import g4hunterpy3; print(g4hunterpy3.__version__)".