2.5 KiB
2.5 KiB
Coding Conventions
These are the rules a contributor needs in their head before touching Vigilar.
They are distilled from CLAUDE.md and from the patterns already in the codebase.
Language and style
- Python 3.11+.
- Ruff for linting. Line length 100 (see
pyproject.toml). - Type hints on all public functions. Internal helpers may omit them when the types are obvious from context.
- No docstrings unless the logic is non-obvious. Short, well-named functions should speak for themselves.
String constants
All string constants referenced in more than one place live in
vigilar/constants.py. The file uses StrEnum for enumerated values —
ArmState, Severity, EventType, SensorType, AlertChannel,
RecordingTrigger, and friends — and a Topics class for MQTT topic builders.
If you are about to write "MOTION_START" or "vigilar/camera/..." in a second
place, stop and add it to the appropriate enum or the Topics class instead.
Defaults like DEFAULT_IDLE_FPS also live in this module.
Database access
- SQLite in WAL mode, opened through
vigilar/storage/db.py. - SQLAlchemy Core expressions only — no mapped classes, no ORM session.
- Schema lives in
vigilar/storage/schema.py. Named query helpers live invigilar/storage/queries.py. - New tables go in
schema.py. New query helpers go inqueries.py. Do not scatter ad-hoc SQL across subsystem code.
Processes and the MQTT bus
- Each subsystem runs in its own
multiprocessing.Process, spawned by the supervisor invigilar/main.pyvia theSubsystemProcesswrapper. Cameras are the exception:CameraManagerowns one child process per camera directly. - Subsystems communicate only through the local MQTT broker at
127.0.0.1:1883. No direct imports or function calls across subsystem boundaries. - Topic naming:
vigilar/<domain>/<id>/<event>. Every topic comes from theTopicsclass invigilar/constants.py— do not construct topic strings ad hoc. - If you are tempted to reach into another subsystem directly, publish a topic instead.
Configuration
config/vigilar.tomlis the only config file the app reads at runtime.- It is validated by Pydantic v2 models in
vigilar/config.py. Add new fields to the Pydantic models, not just to the TOML. - Secrets are file paths, not inline values. Never put a key, password, or token directly in the TOML.
Testing
pytestfrom the repo root.- Tests live under
tests/.
Committing
ruff check vigilar/must pass.pytestmust pass.- One logical change per commit. Commit often.