ffmpeg-go is a Go programming language wrapper for the FFmpeg multimedia framework. It allows developers to easily integrate FFmpeg functionalities into their Go applications, such as decoding and encoding audio and video files, converting media formats, and applying various filters and effects. FFmpeg-go provides a simple and intuitive API, making it easier for Go developers to utilize the powerful multimedia features of FFmpeg.
本质上ffmpeg-go是对命令行ffmpeg工具的封装,最终功能的实现都是通过在go里执行命令行工具来实现。
我们来看个例子。
在go代码中调用ffprobe命令行工具。
Go
// 包装ffprobe工具
// Probe Run ffprobe on the specified file and return a JSON representation of the output.
func Probe(fileName string, kwargs ...KwArgs) (string, error) {
return ProbeWithTimeout(fileName, 0, MergeKwArgs(kwargs))
}
// 为命令行执行ffprobe增加timeout
func ProbeWithTimeout(fileName string, timeOut time.Duration, kwargs KwArgs) (string, error) {
args := KwArgs{
"show_format": "",
"show_streams": "",
"of": "json",
}
return ProbeWithTimeoutExec(fileName, timeOut, MergeKwArgs([]KwArgs{args, kwargs}))
}
// 生成ffprobe命令行执行用到的参数
func ProbeWithTimeoutExec(fileName string, timeOut time.Duration, kwargs KwArgs) (string, error) {
args := ConvertKwargsToCmdLineArgs(kwargs)
args = append(args, fileName)
ctx := context.Background()
// 将超时转换为context控制
if timeOut > 0 {
var cancel func()
ctx, cancel = context.WithTimeout(context.Background(), timeOut)
defer cancel()
}
cmd := exec.CommandContext(ctx, "ffprobe", args...)
buf := bytes.NewBuffer(nil)
stdErrBuf := bytes.NewBuffer(nil)
cmd.Stdout = buf
cmd.Stderr = stdErrBuf
for _, option := range GlobalCommandOptions {
option(cmd)
}
// 运行命令行的命令
// 实际运行的是: ffprobe -of json -show_format -show_streams ${fileName}
err := cmd.Run()
if err != nil {
return "", fmt.Errorf("[%s] %w", string(stdErrBuf.Bytes()), err)
}
return string(buf.Bytes()), nil
}
输出示例:
Go
"streams": [
{
"index": 0,
"codec_name": "h264",
"codec_long_name": "H.264 / AVC / MPEG-4 AVC / MPEG-4 part 10",
"profile": "Main",
"codec_type": "video",
"codec_tag_string": "avc1",
"codec_tag": "0x31637661",
"width": 320,
"height": 240,
"coded_width": 320,
"coded_height": 240,
"closed_captions": 0,
"film_grain": 0,
"has_b_frames": 0,
"sample_aspect_ratio": "1:1",
"display_aspect_ratio": "4:3",
"pix_fmt": "yuv420p",
"level": 13,
"chroma_location": "left",
"field_order": "progressive",
"refs": 1,
"is_avc": "true",
"nal_length_size": "4",
"id": "0x1",
"r_frame_rate": "30000/1001",
"avg_frame_rate": "30000/1001",
"time_base": "1/90000",
"start_pts": 0,
"start_time": "0.000000",
"duration_ts": 627627,
"duration": "6.973633",
"bit_rate": "251413",
"bits_per_raw_sample": "8",
"nb_frames": "209",
"extradata_size": 37,
"disposition": {
"default": 1,
"dub": 0,
"original": 0,
"comment": 0,
"lyrics": 0,
"karaoke": 0,
"forced": 0,
"hearing_impaired": 0,
"visual_impaired": 0,
"clean_effects": 0,
"attached_pic": 0,
"timed_thumbnails": 0,
"captions": 0,
"descriptions": 0,
"metadata": 0,
"dependent": 0,
"still_image": 0
},
"tags": {
"language": "und",
"handler_name": "VideoHandler",
"vendor_id": "[0][0][0][0]"
}
},
{
"index": 1,
"codec_name": "aac",
"codec_long_name": "AAC (Advanced Audio Coding)",
"profile": "LC",
"codec_type": "audio",
"codec_tag_string": "mp4a",
"codec_tag": "0x6134706d",
"sample_fmt": "fltp",
"sample_rate": "44100",
"channels": 2,
"channel_layout": "stereo",
"bits_per_sample": 0,
"initial_padding": 0,
"id": "0x2",
"r_frame_rate": "0/0",
"avg_frame_rate": "0/0",
"time_base": "1/44100",
"start_pts": 0,
"start_time": "0.000000",
"duration_ts": 310272,
"duration": "7.035646",
"bit_rate": "125587",
"nb_frames": "303",
"extradata_size": 2,
"disposition": {
"default": 1,
"dub": 0,
"original": 0,
"comment": 0,
"lyrics": 0,
"karaoke": 0,
"forced": 0,
"hearing_impaired": 0,
"visual_impaired": 0,
"clean_effects": 0,
"attached_pic": 0,
"timed_thumbnails": 0,
"captions": 0,
"descriptions": 0,
"metadata": 0,
"dependent": 0,
"still_image": 0
},
"tags": {
"language": "und",
"handler_name": "SoundHandler",
"vendor_id": "[0][0][0][0]"
}
}
],
"format": {
"filename": "./examples/sample_data/in1.mp4",
"nb_streams": 2,
"nb_programs": 0,
"format_name": "mov,mp4,m4a,3gp,3g2,mj2",
"format_long_name": "QuickTime / MOV",
"start_time": "0.000000",
"duration": "7.035646",
"size": "336833",
"bit_rate": "383001",
"probe_score": 100,
"tags": {
"major_brand": "isom",
"minor_version": "512",
"compatible_brands": "isomiso2avc1mp41",
"encoder": "Lavf57.71.100"
}
}
}