|
16 | 16 |
|
17 | 17 | import asyncio |
18 | 18 | from dataclasses import dataclass |
| 19 | +import inspect |
| 20 | +import logging |
19 | 21 | from typing import Any, AsyncIterator, Optional |
20 | 22 |
|
21 | 23 | import numpy as np |
@@ -397,15 +399,35 @@ def _input_callback(indata: np.ndarray, frame_count: int, time_info: Any, status |
397 | 399 | channels_arg = 1 |
398 | 400 | mapping = [int(input_channel_index) + 1] |
399 | 401 |
|
400 | | - input_stream = sd.InputStream( |
401 | | - callback=_input_callback, |
402 | | - dtype="int16", |
403 | | - channels=channels_arg, |
404 | | - device=input_device, |
405 | | - samplerate=self._in_sr, |
406 | | - blocksize=self._blocksize, |
407 | | - mapping=mapping, |
408 | | - ) |
| 402 | + # Build kwargs and conditionally include 'mapping' based on sounddevice version |
| 403 | + stream_kwargs: dict[str, Any] = { |
| 404 | + "callback": _input_callback, |
| 405 | + "dtype": "int16", |
| 406 | + "channels": channels_arg, |
| 407 | + "device": input_device, |
| 408 | + "samplerate": self._in_sr, |
| 409 | + "blocksize": self._blocksize, |
| 410 | + } |
| 411 | + try: |
| 412 | + init_params = inspect.signature(sd.InputStream.__init__).parameters |
| 413 | + if "mapping" in init_params and mapping is not None: |
| 414 | + stream_kwargs["mapping"] = mapping |
| 415 | + elif mapping is not None: |
| 416 | + logging.getLogger(__name__).warning( |
| 417 | + "sounddevice.InputStream does not support 'mapping' in this version; " |
| 418 | + "ignoring input_channel_index=%s", |
| 419 | + input_channel_index, |
| 420 | + ) |
| 421 | + except Exception: |
| 422 | + # If inspection fails for any reason, fall back without mapping |
| 423 | + if mapping is not None: |
| 424 | + logging.getLogger(__name__).warning( |
| 425 | + "Unable to inspect sounddevice.InputStream.__init__; " |
| 426 | + "ignoring input_channel_index=%s", |
| 427 | + input_channel_index, |
| 428 | + ) |
| 429 | + |
| 430 | + input_stream = sd.InputStream(**stream_kwargs) |
409 | 431 | input_stream.start() |
410 | 432 |
|
411 | 433 | async def _pump() -> None: |
|
0 commit comments