# Capture stdout and stderr in case a command fails

**URL:** <https://discourse.julialang.org/t/capture-stdout-and-stderr-in-case-a-command-fails/101772>\
**Category:** General Usage\
**Tags:** question, cmd, io\
**Created:** [July 19, 2023, 8:26am UTC](https://discourse.julialang.org/t/capture-stdout-and-stderr-in-case-a-command-fails/101772 "2023-07-19T08:26:22Z")\
**Posts on this page:** 3\
**Page:** 1

<div class="post-metadata">

**Author:** ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)\
**Post date:** [July 19, 2023, 8:26am UTC](https://discourse.julialang.org/t/capture-stdout-and-stderr-in-case-a-command-fails/101772/1 "2023-07-19T08:26:22Z")

</div>

What is the current recommended pattern for capturing the output of `stdout` and `stderr` of a command?

I tried something like

```julia
log = IOBuffer()
redirect_stdio(; stdout = log, stderr = log) do
    if success(cmd)
        nothing # things went well, no clutter
    else
        error("stuff failed with output:\n" * String(take!(log)))
    end
end

```

which fails since `IOBuffer` is not an acceptable output for redirection.

---

<div class="post-metadata">

**Author:** ![HanD](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/hand/32/213908_2.png) [@HanD](https://discourse.julialang.org/u/HanD)\
**Post date:** [July 19, 2023, 8:52am UTC](https://discourse.julialang.org/t/capture-stdout-and-stderr-in-case-a-command-fails/101772/2 "2023-07-19T08:52:34Z")

</div>

I used a `Pipe` object instead of an `IOBuffer`. But it seems that `success` eats the stdout, so this won’t work as expected. How about this:

```julia
cmd = `sh -c "echo foobar; false"`
pipe = Pipe()
try
    run(pipeline(cmd; stdout = pipe, stderr = pipe))
catch
    close(pipe.in)
    error("stuff failed with output:\n" * read(pipe, String))
end

```

---

<div class="post-metadata">

**Author:** ![carstenbauer](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/carstenbauer/32/4981_2.png) [@carstenbauer](https://discourse.julialang.org/u/carstenbauer)\
**Post date:** [July 19, 2023, 8:59am UTC](https://discourse.julialang.org/t/capture-stdout-and-stderr-in-case-a-command-fails/101772/3 "2023-07-19T08:59:11Z")

</div>

This is what I use in one of my packages:

```julia
"Run a Cmd object, returning the stdout & stderr contents plus the exit code"
function _execute(cmd::Cmd)
    out = Pipe()
    err = Pipe()

    process = run(pipeline(ignorestatus(cmd); stdout = out, stderr = err))
    close(out.in)
    close(err.in)

    out = (stdout = String(read(out)), stderr = String(read(err)),
           exitcode = process.exitcode)
    return out
end

```
