こうこく
作 ▸
改 ▸

コマンドラインで ffprobe の結果から音声コーデックを取得する

ffmpeg を使って音声の抽出とか色々するスクリプトを書いてたんだけど、コーデックがわからないと音声を抽出できなかったので。

Ubuntu 20.04

そもそもだけど ffprobe の結果って以下のような感じ。

Input #0, mov,mp4,m4a,3gp,3g2,mj2, from 'input.mp4':
  Metadata:
    major_brand     : isom
    minor_version   : 512
    compatible_brands: isomiso2avc1mp41
    encoder         : Lavf58.51.101
  Duration: 00:00:12.07, start: 0.000000, bitrate: 1486 kb/s
    Stream #0:0(und): Video: h264 (High) (avc1 / 0x31637661), yuv420p, 1080x608, 1411 kb/s, 30 fps, 30 tbr, 90k tbn, 60 tbc (default)
    Metadata:
      handler_name    : VideoHandler
    Stream #0:1(und): Audio: aac (LC) (mp4a / 0x6134706D), 44100 Hz, stereo, fltp, 65 kb/s (default)
    Metadata:
      handler_name    : SoundHandler
Input #0, flv, from 'input.flv':
  Duration: 00:04:00.35, start: 0.000000, bitrate: 333 kb/s
    Stream #0:0: Audio: mp3, 22050 Hz, mono, fltp, 65 kb/s
    Stream #0:1: Video: flv1, yuv420p, 320x240, 30 fps, 30 tbr, 1k tbn

これらの Audio: に続く aac とか mp3 だけを取得したかった。

というわけで作ったのが以下のコマンド。

ffprobe input.mp4 2>&1 | awk 'match($0, /Audio: ([^ ]+)( \(.+\))?, /, m) {print m[1]}'

これを実行すると、ffprobe の結果から音声コーデック (aac とか mp3) だけを抜き出せる。

まず 2>&1 だけど、これは ffprobe が何故か結果をstderrに出してくるから、標準出力にまとめて後続の処理に渡せるようにしてる。

そしたら awk で正規表現を使って目的の箇所を抜いてる。Audio: から最初のカンマまでの間に対して、([^ ]+?) で半角スペース以外の文字の連続をキャプチャしてる感じ。aac の場合は aac (LC) (mp4a / 0x6134706D) とかだから、うまいこと aac だけを抜けるように頑張ってる。

あとは match() の結果が m に入ってるから、それを出力してる。丸括弧でキャプチャした文字列はインデックス1以降に入ってるから [1]

おまけ

引数で指定した動画ファイルから音声のみを audio.aac とか audio.mp3 として出力するシェルスクリプト。

#!/bin/bash
cd `dirname $0`

VIDEO_FILE=$1

# 音声コーデック判定
AUDIO_CODEC=`ffprobe ${VIDEO_FILE} 2>&1 | awk 'match($0, /Audio: ([^ ]+)( \(.+\))?, /, m) {print m[1]}'`
if [ -z $AUDIO_CODEC ]; then
	echo "音声コーデックの取得に失敗しました。"
	exit 1
fi

EXTRACTED_AUDIO_FILE=audio.${AUDIO_CODEC}

if [[ -f ./${EXTRACTED_AUDIO_FILE} ]]; then
	echo "${EXTRACTED_AUDIO_FILE} がすでに存在します。"
	exit 1
fi

# 音声抽出
ffmpeg -i ${VIDEO_FILE} -vn -acodec copy ${EXTRACTED_AUDIO_FILE}
if [ "$?" -ne 0 ]; then
	echo "音声抽出に失敗しました。"
	exit 1
fi
この記事に何かあればこちらまで (非公開)