Add vLLM plugin support for high-performance ASR serving

This commit is contained in:
YingboHAO
2026-01-23 17:32:24 +00:00
parent c0c2af984e
commit 4df5b0582f
10 changed files with 2545 additions and 2 deletions
+76 -2
View File
@@ -1,3 +1,6 @@
import os
import threading
import numpy as np
from subprocess import run
from typing import List, Optional, Union, Dict, Any
@@ -57,6 +60,7 @@ def load_audio_use_ffmpeg(file: str, resample: bool = False, target_sr: int = 24
cmd = [
"ffmpeg",
"-loglevel", "error",
"-nostdin",
"-threads", "0",
"-i", file,
@@ -64,14 +68,84 @@ def load_audio_use_ffmpeg(file: str, resample: bool = False, target_sr: int = 24
"-ac", "1",
"-acodec", "pcm_s16le",
"-ar", str(sr_to_use),
"-"
"-",
]
out = run(cmd, capture_output=True, check=True).stdout
out = _run_ffmpeg(cmd).stdout
audio_data = np.frombuffer(out, np.int16).flatten().astype(np.float32) / 32768.0
return audio_data, sr_to_use
def _get_ffmpeg_max_concurrency() -> int:
"""Get the maximum FFmpeg concurrency from environment variable."""
v = os.getenv("VIBEVOICE_FFMPEG_MAX_CONCURRENCY", "")
try:
n = int(v) if v.strip() else 0
except Exception:
n = 0
# 0/negative means no explicit limit.
return n
_FFMPEG_MAX_CONCURRENCY = _get_ffmpeg_max_concurrency()
_FFMPEG_SEM = threading.Semaphore(_FFMPEG_MAX_CONCURRENCY) if _FFMPEG_MAX_CONCURRENCY > 0 else None
def _run_ffmpeg(cmd: list, *, stdin_bytes: bytes = None):
"""Run ffmpeg with optional global concurrency limiting.
This is important for vLLM multi-request concurrency: spawning too many
ffmpeg processes can saturate CPU/IO and cause request failures/timeouts.
"""
if _FFMPEG_SEM is None:
return run(cmd, capture_output=True, check=True, input=stdin_bytes)
with _FFMPEG_SEM:
return run(cmd, capture_output=True, check=True, input=stdin_bytes)
def load_audio_bytes_use_ffmpeg(data: bytes, *, resample: bool = False, target_sr: int = 24000):
"""Decode audio bytes via ffmpeg stdin pipe.
Compared to writing bytes to a temp file, this avoids filesystem IO and
reduces contention under high request concurrency.
Parameters
----------
data: bytes
The audio data bytes
resample: bool
Whether to resample the audio (must be True)
target_sr: int
The target sample rate if resampling is requested
Returns
-------
A tuple containing:
- A NumPy array with the audio waveform in float32 dtype
- The sample rate
"""
if not resample:
# For stdin bytes, we don't have a cheap/robust way to probe original sr.
# Keep behavior explicit.
raise ValueError("load_audio_bytes_use_ffmpeg requires resample=True")
cmd = [
"ffmpeg",
"-loglevel", "error",
"-threads", "0",
"-i", "pipe:0",
"-f", "s16le",
"-ac", "1",
"-acodec", "pcm_s16le",
"-ar", str(target_sr),
"-",
]
out = _run_ffmpeg(cmd, stdin_bytes=data).stdout
audio_data = np.frombuffer(out, np.int16).flatten().astype(np.float32) / 32768.0
return audio_data, target_sr
class AudioNormalizer:
"""
Audio normalization class for VibeVoice tokenizer.