Skip to content

Contributing

Dev workflow and expectations.

Environment setup

Dependencies via uv. Update uv first:

uv self update

If uv self update fails (pip-installed uv, or GitHub API rate limits from cloud/sandbox egress IPs), upgrade from PyPI instead:

python3 -m pip install --user --upgrade uv

Install project + dev + docs groups plus the local-turn (numpy + huggingface_hub, imported by test collection) and local-embed (fastembed, needed at runtime) extras:

uv sync --dev --group docs --extra local-turn --extra local-embed

See Installation for runtime prerequisites (libopus, Discord token, OpenRouter key, Cartesia key, etc.).

TDD workflow

Red / green TDD:

  1. Failing test first (red).
  2. Minimum code to pass (green).
  3. Refactor if needed.

Import errors don't count as red. A test failing on ImportError / ModuleNotFoundError is not a valid red — the module or function must exist before the test can fail for the right reason.

After every code change

Run the same four checks CI runs:

uv sync --dev --extra local-turn --extra local-embed  # sync deps
uv run ruff check             # lint
uv run ruff format            # format
uv run ty check               # type-check
uv run pytest                 # run suite

Or run scripts/ci-local.sh for all of the above in one pass — the same job CI runs.

Cheap on a clean tree. Local failures fail CI the same way — fix root cause before pushing.

Tests marked @pytest.mark.integration hit live services (e.g. OpenRouter) and skip by default. Run explicitly:

uv run pytest -m integration  # needs OPENROUTER_API_KEY etc. in env

Docs build & preview

Built with mkdocs-material. Local preview:

uv run mkdocs serve

Strict build (fails on broken internal links — what CI runs):

uv run mkdocs build --strict

Commit style

  • Conventional prefix (feat:, fix:, docs:, refactor:, test:, chore:) + imperative description.
  • Body explains why, not what — diff shows the what.
  • Keep commits focused. Bug fix shouldn't drag a refactor; refactor shouldn't drag a bug fix.

Scope discipline

  • No features, refactors, or "improvements" beyond the task. Bug fixes don't need surrounding cleanup. Simple features don't need extra configurability.
  • No error handling, fallbacks, or validation for scenarios that can't happen. Trust internal guarantees. Validate only at system boundaries (user input, external APIs).
  • No helpers / abstractions for one-time ops. Three similar lines beats a premature abstraction.
  • No design for hypothetical future requirements. Design decisions holds rejected ideas — check there first.

Where things live