4、音频信息查看:使用 ffprobe 查看音频文件元数据、流信息、编码参数、时长、格式详情
拿到一个音频文件,第一件事是什么?
我个人习惯是先「盘问」它一番——什么格式、什么编码、多长、多少声道、采样率多少。这些信息不搞清楚,后面做任何处理都是盲人摸象。
ffprobe 就是干这个的。它是 FFmpeg 家族里的「侦察兵」,专门用来读取多媒体文件的内部信息。今天我们就把它用透。
4.1 为什么需要 ffprobe?
你想想看,一个 .mp3 文件,表面上看就是个音频。但里面藏着多少东西?
- 容器格式是 MP3 还是 MP4 伪装?
- 编码器是 MP3 还是 AAC?
- 采样率是 44100 还是 48000?
- 码率是 CBR 还是 VBR?
- 有没有内嵌封面图?
- 有没有专辑、艺术家等元数据?
这些用眼睛看不出来,得靠 ffprobe 一条命令搞定。
核心观点:ffprobe 是 FFmpeg 套件中专门用于探测和输出多媒体文件信息的工具。它不会转码、不会修改文件,只读不写,绝对安全。
4.2 基础用法:一条命令看全貌
先来个最简单的。打开终端,输入:
ffprobe input.mp3
输出大概长这样:
Input #0, mp3, from 'input.mp3':
Metadata:
title : 晴天
artist : 周杰伦
album : 叶惠美
date : 2003
Duration: 00:04:29.78, start: 0.000000, bitrate: 192 kb/s
Stream #0:0: Audio: mp3, 44100 Hz, stereo, s16p, 192 kb/s
嗯,信息很全。但说实话,这个输出格式有点「人类友好但机器不友好」。如果你要写脚本批量处理,或者只想提取某个字段,就得用更精准的参数。
4.3 输出格式控制:JSON 和 XML
我个人做自动化脚本时,几乎只用 JSON 输出。结构清晰,解析方便。
ffprobe -v quiet -print_format json -show_format -show_streams input.mp3
参数拆解:
-v quiet:只输出结果,不输出日志和警告-print_format json:输出 JSON 格式-show_format:显示容器格式信息-show_streams:显示所有流信息
输出 JSON 片段示例:
{
"streams": [
{
"index": 0,
"codec_name": "mp3",
"codec_long_name": "MP3 (MPEG audio layer 3)",
"sample_rate": "44100",
"channels": 2,
"channel_layout": "stereo",
"bit_rate": "192000",
"duration": "269.780000"
}
],
"format": {
"filename": "input.mp3",
"format_name": "mp3",
"duration": "269.780000",
"size": "6480000",
"bit_rate": "192000"
}
}
XML 格式也支持,加 -print_format xml 就行。但我建议你直接用 JSON,几乎所有编程语言都有现成的解析库。
4.4 只看你关心的字段
有时候你只想知道时长,或者只想知道采样率。ffprobe 提供了精确提取的选项。
4.4.1 只看时长
ffprobe -v error -show_entries format=duration -of default=noprint_wrappers=1:nokey=1 input.mp3
输出:269.780000(单位:秒)
4.4.2 只看采样率和声道数
ffprobe -v error -show_entries stream=sample_rate,channels -of default=noprint_wrappers=1:nokey=1 input.mp3
输出:
44100
2
4.4.3 只看编码器名称
ffprobe -v error -show_entries stream=codec_name -of default=noprint_wrappers=1:nokey=1 input.mp3
输出:mp3
小技巧:-of default=noprint_wrappers=1:nokey=1 这个参数组合的意思是「只输出值,不输出键名,不包装」。这样拿到的结果可以直接赋值给变量,省去解析步骤。
4.5 查看元数据(Metadata)
音频文件里经常藏着专辑封面、歌手、曲目号等信息。这些属于元数据,不是流数据。
ffprobe -v quiet -print_format json -show_format input.mp3
在 JSON 的 format.tags 字段里,你会看到:
"tags": {
"title": "晴天",
"artist": "周杰伦",
"album": "叶惠美",
"date": "2003",
"genre": "Pop",
"track": "1/10"
}
我曾经帮一个音乐 App 团队排查过问题——用户上传的歌曲封面图显示不出来。一查才发现,有些文件的封面图不是嵌在元数据里,而是作为独立流存在的。这时候得用 -show_streams 才能看到。
4.6 查看流信息(Stream Info)
一个音频文件可能包含多个流。比如一个 MP4 文件,既有音频流又有视频流(封面图动画)。
ffprobe -v quiet -print_format json -show_streams input.mp4
输出中每个流都有一个 index 和 codec_type。你可以根据 codec_type 区分:
"codec_type": "audio"—— 音频流"codec_type": "video"—— 视频流(封面图也算)
每个音频流还会包含:
| 字段 | 含义 | 示例值 |
|---|---|---|
codec_name |
编码器名称 | aac, mp3, flac |
sample_rate |
采样率(Hz) | 44100, 48000 |
channels |
声道数 | 1(单声道), 2(立体声) |
channel_layout |
声道布局 | stereo, mono, 5.1 |
bit_rate |
码率(bps) | 128000, 192000 |
duration |
时长(秒) | 269.78 |
4.7 查看编码参数详情
有些编码参数藏得比较深。比如 AAC 的编码档次(LC、HE、HEv2),或者 MP3 的编码模式(CBR、VBR)。
用 -show_streams 加上 -show_entries stream=codec_name,profile,bit_rate:
ffprobe -v quiet -print_format json -show_entries stream=codec_name,profile,bit_rate input.aac
输出:
"profile": "LC"
嗯,LC 是低复杂度档次,最常见。如果是 HE(高效档次),说明文件用了 SBR(频带复制)技术,适合低码率场景。
注意:不是所有编码器都会暴露 profile 字段。比如 MP3 就没有 profile 概念,只有 MPEG 版本(Layer 1/2/3)。ffprobe 能显示什么,取决于文件本身和封装格式。
4.8 查看格式详情
格式信息指的是容器层面的数据,比如文件格式、总大小、总码率、起始时间等。
ffprobe -v quiet -print_format json -show_format input.flac
关键字段:
| 字段 | 含义 | 示例值 |
|---|---|---|
format_name |
容器格式 | flac, mp3, mov, mp4 |
duration |
总时长(秒) | 269.78 |
size |
文件大小(字节) | 6480000 |
bit_rate |
总码率(bps) | 192000 |
start_time |
起始时间(秒) | 0.000000 |
这里有个坑:bit_rate 是总码率,包含所有流(音频+视频+字幕)。如果你只想要音频流的码率,得去 streams 里找。
4.9 实战:一键生成音频信息报告
我经常写一个脚本,把上面所有信息汇总成一个可读的报告。这里给个 Shell 示例:
#!/bin/bash
FILE="$1"
echo "========== 音频信息报告 =========="
echo "文件: $FILE"
echo ""
echo "--- 格式信息 ---"
ffprobe -v error -show_entries format=format_name,duration,size,bit_rate -of default=noprint_wrappers=1 "$FILE"
echo ""
echo "--- 流信息 ---"
ffprobe -v error -show_entries stream=index,codec_name,codec_type,sample_rate,channels,channel_layout,bit_rate,duration -of default=noprint_wrappers=1 "$FILE"
echo ""
echo "--- 元数据 ---"
ffprobe -v error -show_entries format_tags=title,artist,album,date,genre -of default=noprint_wrappers=1 "$FILE"
echo "================================"
运行 ./audio_info.sh input.mp3,一目了然。
4.10 本章知识体系
下面这张图帮你理清 ffprobe 的信息结构:
4.11 避坑指南
最后分享几个我踩过的坑:
- 坑一:时长不准。 有些 VBR(可变码率)的 MP3 文件,ffprobe 显示的时长是估算值,可能差几秒。这时候用
-show_entries format=duration拿到的值更可靠。 - 坑二:元数据乱码。 中文标签在终端里可能显示为
\uXXXX转义序列。加-print_format json后,JSON 会正确处理 Unicode,但终端输出可能还是乱码。建议重定向到文件查看。 - 坑三:多流文件搞混。 一个文件里有多个音频流(比如多语言音轨),
-show_streams会全部列出。记得用index区分,或者加-select_streams a:0只选第一个音频流。
我的习惯:每次处理新文件,先跑一遍 ffprobe -v quiet -print_format json -show_format -show_streams input.file,把输出存成 JSON 文件。后面写脚本时直接读这个 JSON,不用反复探测,效率高很多。