mirror of
https://github.com/xinnan-tech/xiaozhi-esp32-server.git
synced 2026-07-27 17:43:55 +08:00
Compare commits
1
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
2a9f809700 |
@@ -22,39 +22,45 @@ from config.manage_api_client import report as manage_report
|
||||
TAG = __name__
|
||||
|
||||
|
||||
async def report(conn: "ConnectionHandler", type, text, opus_data, report_time):
|
||||
async def report(conn: "ConnectionHandler", chat_type, text, audio_data, report_time):
|
||||
"""执行聊天记录上报操作
|
||||
|
||||
Args:
|
||||
conn: 连接对象
|
||||
type: 上报类型,1为用户,2为智能体,3为工具调用
|
||||
chat_type: 上报类型,1为用户(ASR/PCM),2为智能体(TTS/Opus),3为工具调用
|
||||
text: 合成文本
|
||||
opus_data: opus音频数据
|
||||
audio_data: 音频数据(chat_type=1时为PCM格式,chat_type=2时为Opus格式)
|
||||
report_time: 上报时间
|
||||
"""
|
||||
try:
|
||||
if opus_data:
|
||||
audio_data = opus_to_wav(conn, opus_data)
|
||||
if audio_data:
|
||||
|
||||
if chat_type == 1:
|
||||
wav_data = pcm_to_wav(conn, audio_data)
|
||||
elif chat_type == 2:
|
||||
wav_data = opus_to_wav(conn, audio_data)
|
||||
else:
|
||||
wav_data = None
|
||||
else:
|
||||
audio_data = None
|
||||
wav_data = None
|
||||
# 执行异步上报
|
||||
await manage_report(
|
||||
mac_address=conn.device_id,
|
||||
session_id=conn.session_id,
|
||||
chat_type=type,
|
||||
chat_type=chat_type,
|
||||
content=text,
|
||||
audio=audio_data,
|
||||
audio=wav_data,
|
||||
report_time=report_time,
|
||||
)
|
||||
except Exception as e:
|
||||
conn.logger.bind(tag=TAG).error(f"聊天记录上报失败: {e}")
|
||||
|
||||
|
||||
def opus_to_wav(conn: "ConnectionHandler", pcm_data):
|
||||
def pcm_to_wav(conn: "ConnectionHandler", pcm_data):
|
||||
"""将PCM数据转换为WAV格式的字节流
|
||||
|
||||
Args:
|
||||
output_dir: 输出目录(保留参数以保持接口兼容)
|
||||
conn: 连接对象
|
||||
pcm_data: PCM音频数据(可能是列表或bytes)
|
||||
|
||||
Returns:
|
||||
@@ -96,11 +102,62 @@ def opus_to_wav(conn: "ConnectionHandler", pcm_data):
|
||||
raise
|
||||
|
||||
|
||||
def opus_to_wav(conn: "ConnectionHandler", opus_data):
|
||||
"""将Opus数据转换为WAV格式的字节流
|
||||
|
||||
Args:
|
||||
conn: 连接对象
|
||||
opus_data: Opus音频数据(可能是列表或bytes)
|
||||
|
||||
Returns:
|
||||
bytes: WAV格式的音频数据
|
||||
"""
|
||||
decoder = None
|
||||
try:
|
||||
decoder = opuslib_next.Decoder(16000, 1)
|
||||
pcm_data = []
|
||||
|
||||
if isinstance(opus_data, list):
|
||||
for opus_packet in opus_data:
|
||||
try:
|
||||
pcm_frame = decoder.decode(opus_packet, 960)
|
||||
pcm_data.append(pcm_frame)
|
||||
except opuslib_next.OpusError as e:
|
||||
conn.logger.bind(tag=TAG).error(f"Opus解码错误: {e}", exc_info=True)
|
||||
elif isinstance(opus_data, bytes):
|
||||
pcm_frame = decoder.decode(opus_data, 960)
|
||||
pcm_data.append(pcm_frame)
|
||||
|
||||
if not pcm_data:
|
||||
raise ValueError("没有有效的音频数据")
|
||||
|
||||
pcm_data_bytes = b"".join(pcm_data)
|
||||
|
||||
wav_header = bytearray()
|
||||
wav_header.extend(b"RIFF")
|
||||
wav_header.extend((36 + len(pcm_data_bytes)).to_bytes(4, "little"))
|
||||
wav_header.extend(b"WAVE")
|
||||
wav_header.extend(b"fmt ")
|
||||
wav_header.extend((16).to_bytes(4, "little"))
|
||||
wav_header.extend((1).to_bytes(2, "little"))
|
||||
wav_header.extend((1).to_bytes(2, "little"))
|
||||
wav_header.extend((16000).to_bytes(4, "little"))
|
||||
wav_header.extend((32000).to_bytes(4, "little"))
|
||||
wav_header.extend((2).to_bytes(2, "little"))
|
||||
wav_header.extend((16).to_bytes(2, "little"))
|
||||
wav_header.extend(b"data")
|
||||
wav_header.extend(len(pcm_data_bytes).to_bytes(4, "little"))
|
||||
|
||||
return bytes(wav_header) + pcm_data_bytes
|
||||
finally:
|
||||
if decoder is not None:
|
||||
try:
|
||||
del decoder
|
||||
except Exception as e:
|
||||
conn.logger.bind(tag=TAG).debug(f"释放decoder资源时出错: {e}")
|
||||
|
||||
|
||||
def enqueue_tts_report(conn: "ConnectionHandler", text, opus_data):
|
||||
if not conn.read_config_from_api or conn.need_bind or not conn.report_tts_enable:
|
||||
return
|
||||
if conn.chat_history_conf == 0:
|
||||
return
|
||||
"""将TTS数据加入上报队列
|
||||
|
||||
Args:
|
||||
@@ -108,6 +165,10 @@ def enqueue_tts_report(conn: "ConnectionHandler", text, opus_data):
|
||||
text: 合成文本
|
||||
opus_data: opus音频数据
|
||||
"""
|
||||
if not conn.read_config_from_api or conn.need_bind or not conn.report_tts_enable:
|
||||
return
|
||||
if conn.chat_history_conf == 0:
|
||||
return
|
||||
try:
|
||||
# 使用连接对象的队列,传入文本和二进制数据而非文件路径
|
||||
if conn.chat_history_conf == 2:
|
||||
@@ -164,10 +225,6 @@ def enqueue_tool_report(conn: "ConnectionHandler", tool_name: str, tool_input: d
|
||||
|
||||
|
||||
def enqueue_asr_report(conn: "ConnectionHandler", text, opus_data):
|
||||
if not conn.read_config_from_api or conn.need_bind or not conn.report_asr_enable:
|
||||
return
|
||||
if conn.chat_history_conf == 0:
|
||||
return
|
||||
"""将ASR数据加入上报队列
|
||||
|
||||
Args:
|
||||
@@ -175,6 +232,10 @@ def enqueue_asr_report(conn: "ConnectionHandler", text, opus_data):
|
||||
text: 合成文本
|
||||
opus_data: opus音频数据
|
||||
"""
|
||||
if not conn.read_config_from_api or conn.need_bind or not conn.report_asr_enable:
|
||||
return
|
||||
if conn.chat_history_conf == 0:
|
||||
return
|
||||
try:
|
||||
# 使用连接对象的队列,传入文本和二进制数据而非文件路径
|
||||
if conn.chat_history_conf == 2:
|
||||
|
||||
Reference in New Issue
Block a user