101 lines
5.5 KiB
Markdown
101 lines
5.5 KiB
Markdown
[](https://github.com/blax-software)
|
|
|
|
# Laravel WebRTC
|
|
|
|
[](https://php.net)
|
|
[](https://laravel.com)
|
|
[](https://github.com/blax-software/reactphp-kernel)
|
|
[](#testing)
|
|
[](#testing)
|
|
[](LICENSE)
|
|
|
|
WebRTC for Laravel on the shared [`reactphp-kernel`](https://github.com/blax-software/reactphp-kernel) backbone. PHP owns **signaling + orchestration**; a pluggable **media engine** owns the real-time media (ICE/DTLS/SRTP/RTP/Opus) — with the production engine backed by a **Rust core (`str0m`) via `ext-php-rs`**, so PHP never runs per-20ms DSP.
|
|
|
|
## Features
|
|
|
|
- 🎙️ **Record / intercept / log** — the engine terminates media server-side, so every participant's audio (human or AI) can be captured
|
|
- 🤖 **AI realtime, provider hidden** — bridge a caller to an external realtime model (e.g. OpenAI Realtime) over a server-side socket; the browser only ever talks to *you*, and the model is a config swap
|
|
- 👥 **Party-to-party & group calls** — `join`/`leave` a room and the `RoomManager` meshes each new peer with everyone already there (instructor↔student, controller↔pilot, guest↔admin)
|
|
- 🧩 **On the shared kernel** — signaling runs on `reactphp-kernel` alongside your WebSockets, one process, one loop
|
|
- 🔌 **Pluggable `MediaEngine`** — `NullMediaEngine` for signaling-only dev; `Str0mMediaEngine` for the real Rust-backed media
|
|
- 🦀 **Rust media core** — `str0m` (sans-IO WebRTC) via `ext-php-rs`, shipped in `rust/`
|
|
- 🎛️ **Transport-agnostic signaling** — route browser frames from this package's raw server or from `laravel-websockets` into the same handler
|
|
|
|
## Installation
|
|
|
|
```bash
|
|
composer require blax-software/laravel-webrtc
|
|
php artisan vendor:publish --tag="webrtc-config"
|
|
```
|
|
|
|
It depends on [`blax-software/reactphp-kernel`](https://github.com/blax-software/reactphp-kernel), resolved from git.blax.at via the `repositories` entry in `composer.json`.
|
|
|
|
## Quick Start
|
|
|
|
Run the signaling server (on the shared kernel):
|
|
|
|
```bash
|
|
php artisan webrtc:serve
|
|
```
|
|
|
|
With the default `NullMediaEngine`, signaling runs and the engine refuses `offer()` loudly. Build the Rust core (see [`rust/README.md`](rust/README.md)) and switch the engine for real calls:
|
|
|
|
```dotenv
|
|
WEBRTC_MEDIA_ENGINE="Blax\WebRtc\Media\Str0mMediaEngine"
|
|
```
|
|
|
|
### Signaling wire shape (newline-delimited JSON)
|
|
|
|
```jsonc
|
|
{ "type": "offer", "peer": "p1", "sdp": "..." } // -> { "type": "answer", "peer": "p1", "sdp": "..." }
|
|
{ "type": "ice", "peer": "p1", "candidate": {...} } // (no reply)
|
|
{ "type": "record", "peer": "p1", "path": "..." } // -> { "type": "ack", ... }
|
|
{ "type": "connect", "peer": "p1", "other": "p2" } // low-level: mesh two peers
|
|
{ "type": "join", "peer": "p1", "room": "lobby" } // -> { "type": "joined", "peers": [...] } (auto-meshes)
|
|
{ "type": "leave", "peer": "p1" } // -> { "type": "left", "peers": [...] }
|
|
{ "type": "bridge", "peer": "p1", "options": {...} } // dial an external realtime model
|
|
{ "type": "close", "peer": "p1" } // closes media + leaves the room
|
|
```
|
|
|
|
`SignalingHandler` is transport-agnostic — feed it frames from the built-in raw `SignalingServer` today, or from the `laravel-websockets` WS transport (for browsers) later, without changing the media wiring.
|
|
|
|
## Configuration
|
|
|
|
`config/webrtc.php` covers the signaling bind (`host`/`port`/`tls`), the `media_engine` binding, `recording` disk/path, advertised `ice_servers`, and the external `bridge` (e.g. OpenAI model + key). Swapping the realtime model — or the whole provider — is a server-side config change the browser never sees.
|
|
|
|
## Status
|
|
|
|
**MVP scaffold.** Signaling + the engine abstraction are real, tested, and runnable with `NullMediaEngine`; the `Str0mMediaEngine` + `rust/` core are the seam to build next. This is the WebRTC half of the blax realtime stack.
|
|
|
|
## Architecture
|
|
|
|
```
|
|
reactphp-kernel shared backbone (loop, IPC, signals)
|
|
└─ laravel-webrtc (this) signaling on the kernel
|
|
├─ NullMediaEngine signaling-only (dev/tests)
|
|
└─ Str0mMediaEngine Rust/str0m core via ext-php-rs (rust/)
|
|
```
|
|
|
|
## Testing
|
|
|
|
```bash
|
|
composer install
|
|
composer test
|
|
```
|
|
|
|
The signaling router and engines are unit-tested against a fake media engine — no browser, sockets, or external services required.
|
|
|
|
## License
|
|
|
|
MIT. See [LICENSE](LICENSE).
|
|
|
|
## Star History
|
|
|
|
<a href="https://www.star-history.com/?repos=blax-software%2Flaravel-webrtc&type=date&legend=top-left">
|
|
<picture>
|
|
<source media="(prefers-color-scheme: dark)" srcset="https://api.star-history.com/chart?repos=blax-software/laravel-webrtc&type=date&theme=dark&legend=top-left" />
|
|
<source media="(prefers-color-scheme: light)" srcset="https://api.star-history.com/chart?repos=blax-software/laravel-webrtc&type=date&legend=top-left" />
|
|
<img alt="Star History Chart" src="https://api.star-history.com/chart?repos=blax-software/laravel-webrtc&type=date&legend=top-left" />
|
|
</picture>
|
|
</a>
|