如何在Python中无磁盘IO、不使用FFmpeg转换Opus编码OGG字节数组为WAV?
将Opus编码的OGG字节数组内存转WAV(Python,无磁盘IO/FFmpeg)
需求说明
需要在Python中处理Telegram API获取的Opus编码OGG字节数组,直接在内存中转换为WAV格式字节数组,要求:
- 不写入磁盘以消除IO延迟
- 不依赖FFmpeg工具
当前实现通过磁盘存储+FFmpeg转换,不符合需求,需基于download_as_bytearray()获取的字节数组完成内存转换。
解决方案:使用pyogg+wave库
安装依赖
pip install pyogg
注:
wave是Python标准库,无需额外安装
完整代码实现
import pyogg import wave from io import BytesIO from telegram import Update from telegram.ext import ContextTypes async def audio(update: Update, context: ContextTypes.DEFAULT_TYPE): # 从Telegram下载OGG音频字节数组 newFile = await context.bot.get_file(update.message.voice.file_id) ogg_byte_array = await newFile.download_as_bytearray() # 将字节数组包装为可读取的流对象 ogg_stream = BytesIO(ogg_byte_array) # 解码Opus OGG为PCM原始音频数据 opus_file = pyogg.OpusFile(ogg_stream) # 获取numpy数组格式的PCM数据,后续转字节流 pcm_data = opus_file.as_array() # 在内存中构建WAV格式字节流 wav_stream = BytesIO() with wave.open(wav_stream, 'wb') as wav_handler: # 配置WAV参数:声道数、采样宽度(16位=2字节)、采样率 wav_handler.setnchannels(opus_file.channels) wav_handler.setsampwidth(2) wav_handler.setframerate(opus_file.frequency) # 写入PCM原始数据 wav_handler.writeframes(pcm_data.tobytes()) # 获取最终的WAV字节数组 wav_byte_array = wav_stream.getvalue() # 此处可添加WAV字节数组的后续处理逻辑(如语音识别、存储等) print(f"转换完成,WAV字节数组大小:{len(wav_byte_array)} 字节")
关键步骤说明
- 字节流处理:用
BytesIO将字节数组转为可随机读取的流,适配pyogg的输入要求 - Opus解码:
pyogg.OpusFile直接解码OGG流,输出标准16位PCM数据(numpy数组格式) - WAV生成:通过
wave模块在内存中创建WAV文件,写入PCM数据后提取字节数组,全程无磁盘操作
内容的提问来源于stack exchange,提问作者Ramish Rasool
相关产品推荐
相关产品推荐

