Contributing
Reporting issues
- Bug? Use the bug report template — run
meridian doctorfirst - Connection issue? Use the connection issue template — run
meridian testandmeridian preflightfirst - Feature idea? Use the feature request template
- Security vulnerability? See Security — do NOT open a public issue
Development setup
git clone https://github.com/uburuntu/meridian.git && cd meridian
# Install CLI in editable mode with dev dependencies
make install
# Install pre-push hook (11 fast checks before every push)
make hooks
# Run full CI locally
make ci
# Individual checks:
make test # pytest
make lint # ruff check
make format-check # ruff format --check
make typecheck # mypy
make templates # Jinja2 template validation
Project structure
The CLI is a Python package (src/meridian/) distributed via PyPI as meridian-vpn.
Key modules:
cli.py— Typer app, subcommand registrationcommands/— one module per subcommandcredentials.py—ServerCredentialsdataclassservers.py—ServerRegistryfor known serversprovision/— idempotent step pipeline
Pull requests
- Fork the repo and create a branch from
main - Make focused, minimal changes
- Ensure CI passes:
make ci - Test on a real server if possible
- Open a PR with a clear description
Key conventions
- Shell values use
shlex.quote()— never interpolate unsanitized values - Connection-info templates must stay in sync (CSS/JS/app links)
- Caddy config goes in
/etc/caddy/conf.d/meridian.caddy, not the main Caddyfile - Provisioner steps return
StepResult(ok/changed/skipped/failed)
Testing
CI validates: Python tests, ruff lint, mypy types, template rendering, and shell script syntax. Full deployment testing requires a real VPS.