Files
rutster/crates/rutster-tap/src/lib.rs
A.D.Lee c30a45232d
All checks were successful
CI / fmt (push) Successful in 1m40s
CI / clippy (push) Successful in 2m24s
CI / test (1.85) (push) Successful in 5m8s
CI / test (stable) (push) Successful in 5m20s
CI / deny (push) Successful in 1m34s
Slice 3 — OpenAI Realtime brain: swap echo for the brain (#4)
2026-07-01 22:25:09 +00:00

58 lines
2.6 KiB
Rust

//! # rutster-tap
//!
//! The agent tap: core-as-client + brain-as-server (spec §2, ADR-0006).
//! Slice-1 pre-paved the seam by exposing the canonical PCM boundary as
//! the `AudioSource` / `AudioSink` traits in [`rutster_media`](../rutster-media/index.html),
//! wired by an in-process `EchoAudioPipe`. Slice-2 (this crate) swaps that
//! pipe for a real WSS tap client. No code changes to `RtcSession` itself
//! in step 2 — that's the test of the seam (slice-1 §3.3).
//!
//! # Layout
//!
//! - [`protocol`]: the versioned JSON event wire format (spec §3). PCM
//! is base64-encoded little-endian i16 (spec §3, §9).
//! - `tap_audio_pipe` (Task 3): the sync `AudioSource`/`AudioSink` impl over
//! mpsc + a bounded playout ring (spec §4.1). The seam object `RtcSession`
//! holds; the slice-1 `loop_driver` calls it via `next_pcm_frame` /
//! `on_pcm_frame` exactly as before.
//! - `tap_client` (Task 3/4): the async WSS connection driver. Runs inside the
//! `TapEngine` task (in the binary crate); the media loop never sees it.
//! - `metrics` (Task 4): atomic counters — the "observe" half of "drop +
//! observe" (slice-1 §3.8 extended to the tap wire).
//!
//! # Dependency direction
//!
//! `rutster-tap` → `rutster-media` (re-exports `PcmFrame`; one canonical
//! home — spec §2.1). `rutster-media` does NOT depend on `rutster-tap`
//! — that would invert the canonical-home of `PcmFrame` and pull the
//! loopback peer into the tap story.
pub mod metrics;
pub mod protocol;
pub mod tap_audio_pipe;
pub mod tap_client;
// Re-export PcmFrame so `rutster-tap` consumers (the binary, the echo brain,
// future brains) get it from one canonical home (spec §3.1).
pub use rutster_media::PcmFrame;
pub use metrics::{MetricsSnapshot, TAP_PLAYOUT_FRAMES, TapMetrics};
pub use protocol::{
AudioPayload, DecodedFrame, DecodedPayload, Envelope, ErrorPayload, FrameKind, HelloPayload,
PROTOCOL_VERSION, Payload, ReasonPayload, SAMPLES_PER_FRAME as WIRE_SAMPLES_PER_FRAME,
SessionEndPayload, TapProtoError, decode_envelope, decode_pcm, encode_audio_in,
encode_audio_out, encode_bye, encode_error, encode_function_call, encode_function_call_output,
encode_hello, encode_pcm, encode_session_end, encode_speech_started, encode_speech_stopped,
encode_tools_update,
};
// Slice-3 additive (spec §3).
pub use protocol::{FunctionCallOutputPayload, FunctionCallPayload, ToolsUpdatePayload};
pub use tap_audio_pipe::TapAudioPipe;
pub use tap_client::{FunctionCallEvent, FunctionCallOutputEvent, TapClientError, run_tap_client};
#[cfg(test)]
mod tests {
#[test]
fn crate_compiles() {}
}