ASR句首丢字问题 (#346)

* fix: ASR句首丢字问题 (#338)

* feat: 支持dify的多轮对话, chat工作流支持持久化conversation_id #296 (#313)

* TTS功能的一些修改 (#307)

* fix: tts音频转码兼容

* feat: 支持自定义tts接口服务

* feat: tts超时时间作为可配置项

* feat: 自定义tts音频格式兼容

* style: 使命名更符合语义

---------

Co-authored-by: Jad <i@nocilol.me>
Co-authored-by: yanyige <yige.yan@qq.com>
Co-authored-by: Jad <journey.adc@gmail.com>
This commit is contained in:
欣南科技
2025-03-15 00:19:45 +08:00
committed by GitHub
co-authored by Jad yanyige Jad
parent fc3f982309
commit 50ecee99cc
7 changed files with 75 additions and 13 deletions
@@ -41,19 +41,20 @@ class TTSProviderBase(ABC):
async def text_to_speak(self, text, output_file):
pass
def wav_to_opus_data(self, wav_file_path):
# 使用pydub加载PCM文件
def audio_to_opus_data(self, audio_file_path):
"""音频文件转换为Opus编码"""
# 获取文件后缀名
file_type = os.path.splitext(wav_file_path)[1]
file_type = os.path.splitext(audio_file_path)[1]
if file_type:
file_type = file_type.lstrip('.')
audio = AudioSegment.from_file(wav_file_path, format=file_type)
audio = AudioSegment.from_file(audio_file_path, format=file_type)
# 转换为单声道/16kHz采样率/16位小端编码(确保与编码器匹配)
audio = audio.set_channels(1).set_frame_rate(16000).set_sample_width(2)
# 音频时长(秒)
duration = len(audio) / 1000.0
# 转换为单声道和16kHz采样率(确保与编码器匹配)
audio = audio.set_channels(1).set_frame_rate(16000)
# 获取原始PCM数据(16位小端)
raw_data = audio.raw_data
@@ -0,0 +1,35 @@
import os
import uuid
import requests
from config.logger import setup_logging
from datetime import datetime
from core.providers.tts.base import TTSProviderBase
TAG = __name__
logger = setup_logging()
class TTSProvider(TTSProviderBase):
def __init__(self, config, delete_audio_file):
super().__init__(config, delete_audio_file)
self.url = config.get("url")
self.headers = config.get("headers", {})
self.params = config.get("params")
self.format = config.get("format", "wav")
self.output_file = config.get("output_file", "tmp/")
def generate_filename(self):
return os.path.join(self.output_file, f"tts-{datetime.now().date()}@{uuid.uuid4().hex}.{self.format}")
async def text_to_speak(self, text, output_file):
request_params = {}
for k, v in self.params.items():
if isinstance(v, str) and "{prompt_text}" in v:
v = v.replace("{prompt_text}", text)
request_params[k] = v
resp = requests.get(self.url, params=request_params, headers=self.headers)
if resp.status_code == 200:
with open(output_file, "wb") as file:
file.write(resp.content)
else:
logger.bind(tag=TAG).error(f"Custom TTS请求失败: {resp.status_code} - {resp.text}")