Sxian/clt 2919/integrate platform audio#669
Conversation
f519dde to
52bed9f
Compare
- Update rust-sdks submodule to latest main (497527d4) - Regenerate protobuf files - Includes: Fix LocalTrackPublished handle leak, WebRTC ADM integration, and other improvements Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
52bed9f to
2ef05f0
Compare
|
@copilot, please check the |
356d5c0 to
e118dc5
Compare
| prefer_hardware: Prefer hardware audio processing when available. | ||
| - iOS: Uses Voice Processing I/O (VPIO) for low-latency processing | ||
| - Android: Hardware support varies by device | ||
| - Desktop: Generally not available | ||
| Default: True on iOS, False on other platforms. | ||
| """ | ||
|
|
||
| echo_cancellation: bool = True | ||
| noise_suppression: bool = True | ||
| auto_gain_control: bool = True | ||
| prefer_hardware: bool = False |
There was a problem hiding this comment.
🚩 PlatformAudioOptions.prefer_hardware default vs proto documentation discrepancy
The proto comment for prefer_hardware in audio_frame_pb2.pyi:975-977 says Default: true and the PlatformAudioOptions docstring says Default: True on iOS, False on other platforms, but the Python dataclass default is prefer_hardware: bool = False. Since _to_proto() always explicitly sets this field, the FFI backend will always receive False unless the user overrides it — the backend never gets the chance to apply platform-specific defaults. This may be intentional (letting the Python SDK control the value explicitly), but the docstring claiming 'Default: True on iOS' is misleading since the Python default is unconditionally False.
Was this helpful? React with 👍 or 👎 to provide feedback.
| prefer_hardware: bool = False | ||
|
|
||
| def _to_proto(self) -> proto_audio_frame.AudioSourceOptions: | ||
| return proto_audio_frame.AudioSourceOptions( | ||
| echo_cancellation=self.echo_cancellation, | ||
| noise_suppression=self.noise_suppression, | ||
| auto_gain_control=self.auto_gain_control, | ||
| prefer_hardware=self.prefer_hardware, | ||
| ) |
There was a problem hiding this comment.
🟡 _to_proto() always explicitly sets prefer_hardware=False, overriding server-side platform-specific defaults
The PlatformAudioOptions dataclass defaults prefer_hardware to False and _to_proto() always sets it explicitly in the proto message. Because the proto field uses optional semantics (verified: HasField('prefer_hardware') returns True when explicitly set to False vs False when unset), the server can distinguish "not set" from "explicitly false". The proto comment at livekit-rtc/livekit/rtc/_proto/audio_frame_pb2.pyi:984 says the server default is true (hardware-accelerated VPIO on iOS). By always sending an explicit False, the Python SDK prevents the server from ever applying its recommended platform-specific defaults. The docstring at line 121 compounds this by claiming "Default: True on iOS, False on other platforms" — behavior the code doesn't implement.
Fix approach
Use Optional[bool] for prefer_hardware with a default of None, and only set the proto field when the user explicitly specifies a value. This lets the server apply its own platform-specific defaults when the user hasn't expressed a preference.
Prompt for agents
The prefer_hardware field in PlatformAudioOptions defaults to False and is always sent explicitly to the server via _to_proto(). Since the proto field uses optional semantics (proto3 optional), the server can distinguish 'not set' from 'explicitly set to false'. The proto comment says the server's default is true (for iOS VPIO hardware acceleration). By always sending an explicit False, the SDK overrides the server's platform-specific defaults.
The fix involves:
1. In PlatformAudioOptions (platform_audio.py line 127), change prefer_hardware from bool = False to Optional[bool] = None
2. In _to_proto() (platform_audio.py lines 129-135), only set prefer_hardware in the proto message when self.prefer_hardware is not None
3. Update the docstring (line 121) to clarify that None means 'let the server decide based on platform'
This allows the server to apply its recommended default (True on iOS, False elsewhere) when the user doesn't explicitly specify a preference.
Was this helpful? React with 👍 or 👎 to provide feedback.
Summary
Adds PlatformAudio support to the Python SDK, enabling microphone capture via WebRTC's Audio Device Module (ADM) with built-in voice processing.
Changes
New: livekit-rtc/livekit/rtc/platform_audio.py
Modified: livekit-rtc/livekit/rtc/track.py
Modified: livekit-rtc/livekit/rtc/init.py
Modified: livekit-rtc/livekit/rtc/room.py
Modified: examples/basic_room.py
New: examples/README.md
PlatformAudio vs Synthetic Mode
┌───────────────────────────────┬───────────────┬───────────────────────────────────────┐
│ Feature │ PlatformAudio │ Synthetic │
├───────────────────────────────┼───────────────┼───────────────────────────────────────┤
│ Voice processing (AEC/NS/AGC) │ Built-in │ Manual │
├───────────────────────────────┼───────────────┼───────────────────────────────────────┤
│ Raw frame access │ No │ Yes │
├───────────────────────────────┼───────────────┼───────────────────────────────────────┤
│ External audio libs needed │ No │ Yes │
├───────────────────────────────┼───────────────┼───────────────────────────────────────┤
│ Use case │ Voice calls │ Custom processing, TTS, file playback │
└───────────────────────────────┴───────────────┴───────────────────────────────────────┘
Both modes can run simultaneously (e.g., mic + background music).
Test Procedure
cd examples
python basic_room.py --list-devices
Expected: Lists available microphones and speakers with device IDs.
Start LiveKit server
livekit-server --dev
In another terminal
export LIVEKIT_URL=ws://localhost:7880
export LIVEKIT_API_KEY=devkey
export LIVEKIT_API_SECRET=secret
python basic_room.py --platform-audio --room test-room
Expected: Connects to room, publishes microphone track with voice processing.
python basic_room.py --platform-audio --mic-id "" --room test-room
Expected: Uses specified microphone.
python basic_room.py --file test.wav --room test-room
Expected: Publishes audio from WAV file.
python basic_room.py --platform-audio --file test.wav --room test-room
Expected: Publishes two audio tracks - microphone and file.
Open https://meet.livekit.io and join the same room to verify audio is received.