git clone https://github.com/0xFl4g/wazuh-mcp.git
cd wazuh-mcp
uv sync
uv run pytest tests/unit -q -m "not integration" # 591 PASS, 4 SKIPmainis the integration branch. All PRs targetmain. Feature branches are short-lived.- Atomic commits, scope-prefixed messages. Commit style:
scope(area): subject in imperative mood. Examples:feat(rate_limit): ...,fix(integration): ...,docs(v1.1): .... The body explains why. - No AI-attribution footers. No
Co-Authored-By: Claude, no "Generated with..." trailers. All commits land in the contributor's voice. - TDD-first for non-trivial changes. Write the failing test, get it to fail for the right reason, implement, watch it pass, commit.
- Small PRs. A clean 200-line PR lands faster than a 2000-line one. If a feature is large, split into a series.
Every PR runs:
ci—ruff check,ruff format --check,ty check,pytest tests/unit. Must pass.helm-lint— runs on chart edits. Must pass.security—gitleaks,pip-audit,safety. Must pass.integration— runs nightly + on workflow_dispatch. Touching integration code? Trigger it viagh workflow run integration.ymlbefore requesting review.
- Python 3.12. Type hints required on new code.
ruffconfig inpyproject.tomlis authoritative; selectsE/F/I/UP/B/SIM/RUF/N/ASYNC. - Pydantic models default to
model_config = ConfigDict(extra="forbid", frozen=True)unless mutability is genuinely needed. - Use
# ty: ignorefor type-checker suppressions, not# type: ignore(we usety, not mypy). - Avoid
# noqa: <CODE>for codes not in the project's ruff selects — they triggerRUF100 unused-noqa. Use a plain explanatory comment instead.
- Unit tests in
tests/unit/. Async tests useasyncio_mode = "auto"(no explicit@pytest.mark.asynciodecorator needed but harmless). - Integration tests in
tests/integration/, marked@pytest.mark.integration. Spun up viadocker compose -f docker/integration-compose.yml up -d+ the bootstrap script. - New write-tools (
write.*) require a unit test for the allowlist contract AND an integration test that proves the wire shape. - Cross-subsystem changes (touching tenancy, rate-limiter, audit) require plan-time invariant grep — see prior ship history for the M5a Keycloak claim-mapper / IssuerIndex precedent.
- Operator-facing changes update
docs/deploy/*.md. - New tools update
docs/api-reference.md. - Design docs go in
docs/superpowers/specs/YYYY-MM-DD-<topic>-design.md. Implementation plans indocs/superpowers/plans/. These are intentionally public — they document how decisions were made.
For non-security bugs: open a GitHub issue with the bug label.
For security issues: see SECURITY.md. Do not open a public issue.
Maintainers only. Process:
- Bump
versioninpyproject.toml; runuv lock. - Commit with
chore: bump version X -> Y. - Tag:
git tag -a vX.Y.Z -m "release notes here". - Push
main+ the tag. Thereleaseworkflow publishes to GHCR. - Create a GitHub Release page with formatted notes.