ffmpeg audio files using the stdin / stdout object input or output BytesIO

Recently engaged in small recording program, and then use Baidu to do speech recognition interfaces.

Applet currently only supports mp3 and aac encoding format. Although m4a formats Baidu interface provides direct support programs to identify small audio files, but because he still has a number of other requirements (such as read data directly, perform other processing as needed), I still want to be able to convert m4a files pcm encoded file.

Backend using ffmpeg command as follows:

# 基于文件操作
ffmpeg -n -i input-1576685164r111.m4a -acodec pcm_s16le -f wav -ac 1 -ar 8000 output-8k-mono.wav

But if you download a file from the Internet using Python, (for example, I put the file exists Baidu object store, BOS), you may prefer to use BytesIO this memory file.

Then ffmpeg convert file-based operation requires you to create a temporary file, then convert to remove it, which requires you to operate on the file system, inefficient and cumbersome.

It is time to understand the ffmpeg-based operating stdin, stdout of the:

# 仅输入使用pipe
cat input-1576685164r111.m4a | ffmpeg -n -i pipe: -acodec pcm_s16le -f wav -ac 1 -ar 8000 output-8k-mono.wav
# 或全使用pipe
cat input-1576685164r111.m4a | ffmpeg -n -i pipe: -acodec pcm_s16le -f wav -ac 1 -ar 8000 pipe:

Using python and BytesIO how does it work? Well, I have written:

#!/usr/bin/env python3
# coding: utf-8
#
# Created by dylanchu on 2019/12/20

from io import BytesIO
from subprocess import Popen, PIPE


def m4a2wav_bytes_io(bytes_io_file):
    bytes_io_file.seek(0)
    content = bytes_io_file.getvalue()
    cmd = ['ffmpeg', '-n', '-i', 'pipe:', '-acodec', 'pcm_s16le', '-f', 'wav', '-ac', '1', '-ar', '8000', 'pipe:']
    p = Popen(cmd, stdin=PIPE, stdout=PIPE, stderr=PIPE, bufsize=-1)
    out, _ = p.communicate(input=content)
    p.stdin.close()
    return BytesIO(out) if out.startswith(b'RIFF\xff\xff\xff') else None

_Eliminating that error message, namely ffmpeg other information output.

This piecemeal several reference links provide some help:

https://stackoverflow.com/questions/20321116/can-i-pipe-a-io-bytesio-stream-to-subprocess-popen-in-python
https://stackoverflow.com/questions/49013020/scipy-io --the Read-at The -wavfile stdout-from-ffmpeg
https://segmentfault.com/a/1190000016652277?utm_source=tag-newest
If you want to use front-end js direct conversion format, rather than the back-end conversion:
HTTPS: // segmentfault .com / A / 1190000018200927
https://segmentfault.com/a/1190000018215367

Guess you like

Origin www.cnblogs.com/dylanchu/p/12071158.html