Cookbook¶
Build real things, fast. Each recipe is a complete, working starting point — the YAML config, the Python script, and how to test it — for a common SIP role. They're deliberately small (usually under 60 lines of Python) so you can read the whole thing and adapt it.
Every recipe is grounded in a real script in the repo (linked at the bottom of each page); none of the APIs here are invented.
The recipes¶
| Recipe | What you build | Key ideas |
|---|---|---|
| Registrar | A SIP registrar with digest auth | auth.require_digest, registrar.save/lookup, NAT fixups |
| Stateful proxy | A residential/edge proxy | request.fork, loose_route, record_route, sanity checks |
| Load balancer | A front LB over a backend pool | gateway.select, health probing, subscriber affinity |
| SBC (B2BUA) | A topology-hiding SBC with media | @b2bua.*, call.dial/fork, header policies, RTPEngine |
| Media & RTP profiles | SRTP↔RTP, WebRTC, transcoding, hold | rtpengine.offer/answer, profiles, the sdp namespace |
| Hardening & security | A locked-down edge | rate-limit, scanner/auth bans, TLS/mTLS, STIR/SHAKEN, IPsec |
| Monitoring & observability | Metrics, CDRs, tracing, probes | custom Prometheus metrics, /admin/*, CDR, HEP/Homer |
How to run any recipe¶
Each recipe is a siphon.yaml + a Python script. Point the config at the script and
run siphon:
Scripts hot-reload — edit and save, no restart (except listen: changes). Test
your script logic without a running server using the
siphon-sip mock SDK.
Mixing roles¶
A single script can be several of these at once — the dispatcher routes INVITEs to
your @b2bua.on_invite handler and everything else to @proxy.on_request. So a
"proxy for REGISTER/OPTIONS + SBC for calls" is one script, one process (see the
SBC recipe and the README's hybrid-mode section).
For running more than one node, see Scaling & redundancy and Deployment & operations.