ffmpeg の avfoundation `-list_devices true` は常に非0終了し、デバイス一覧は stdout ではなく stderr(例外オブジェクト経由)に出る
Node.js
ffmpeg
avfoundation
macOS
知識
ffmpeg で macOS の avfoundation 入力デバイス(画面キャプチャ・カメラ)一覧を取得する ffmpeg -f avfoundation -list_devices true -i "" は、正常にデバイス列挙できていても出力先を指定していないため必ず非0で終了する。
誤解しやすい条件
- Node.js の
execFileSyncや同種の同期実行 API でこのコマンドを呼ぶと、非0終了により必ず例外が投げられる。デバイス列挙に成功しているかどうかは終了コードでは判定できず、常に catch 側で処理する前提で書く必要がある。 - デバイス一覧(
[N] Capture screen 0や[N] <カメラ名>のような行)は stdout ではなく stderr に出力される。execFileSync が非0終了時に投げる例外オブジェクトの.stderr(Buffer)から読み取る必要があり、.stdoutを見ても空になる。 - 呼び出し側で
stdioを明示的にignoreにすると、例外オブジェクトに.stderrが付与されず出力を失う。デフォルト(pipe)のまま呼ぶか、明示的に stderr を pipe に設定する。
判断基準
この挙動を前提に、デバイス index(例: 画面キャプチャの「Capture screen N」)を自動検出したい場合は、以下の手順にする。
- コマンドを try/catch で包み、成功パスではなく catch パスでパースする。
- 例外オブジェクトの stderr を文字列化し、対象デバイス名(例:
Capture screen)を含む行を正規表現で抽出する。 - 検出できない場合(出力形式が変わった、環境依存で失敗した等)は固定のデフォルト index にフォールバックする実装にしておくと壊れにくい。
検証方法
実機で該当コマンドを直接実行し、終了コードが非0であること、デバイス一覧が stderr 側に出ていることを確認してから自動化コードに組み込む。自動化コード側では、意図的に無効な index を渡した場合にフォールバックが機能するかも別途確認する。