1. ホーム
  2. error-handling

[解決済み] Golang で exec.Command を実行したときの "exit status 1" エラーをデバッグする方法

2022-02-10 19:30:05

質問

以下のコードを実行すると

cmd := exec.Command("find", "/", "-maxdepth", "1", "-exec", "wc", "-c", "{}", "\\")
var out bytes.Buffer
cmd.Stdout = &out
err := cmd.Run()
if err != nil {
    fmt.Println(err)
    return
}
fmt.Println("Result: " + out.String())

このエラーが発生します。

終了ステータス 1

しかし、これではエラーの正確な原因をデバッグするのに役立ちません。

より詳細な情報を得るには?

解決するには?

解決策としては Stderr プロパティを使用します。これは、次のようにできます。

cmd := exec.Command("find", "/", "-maxdepth", "1", "-exec", "wc", "-c", "{}", "\\")
var out bytes.Buffer
var stderr bytes.Buffer
cmd.Stdout = &out
cmd.Stderr = &stderr
err := cmd.Run()
if err != nil {
    fmt.Println(fmt.Sprint(err) + ": " + stderr.String())
    return
}
fmt.Println("Result: " + out.String())

上記のコードを実行すると、何が問題なのかが明確になります。

<ブロッククオート

終了ステータス 1: find: -exec: 終了する ";" または "+" がありません。

編集してください。

上記のコードでは、エラーが発生した場合、メッセージが標準エラー出力され、コマンドは0以外のエラーコードを返すと想定しています。これは多かれ少なかれ標準的なことです。

しかし、@snorberhuis が後述するように、コマンドによってはエラーが stdout に出力されることがあります。他のコマンドでは、stderr に出力するがエラーコードは 0 を返すかもしれない(その場合 err になります。 nil ). また、標準エラー出力にメッセージがあっても、必ずしもエラーとは限りません(ffmpegのツールではよくあることです)。

ですから、基本的には、あなたが期待するコマンドに対応するために、上記のコードを微調整する必要があるかもしれません。