A Perl 6 module to capture a command's output and exit code.
Perl 6
Switch branches/tags
Nothing to show



Shell::Capture - capture a command's output and exit code


    use Shell::Capture;

    my Shell::Capture $c .= capture('id', '-u', '-n');
    if $c.exitcode != 0 {
        die "Could not execute id -u -n\n";
    } elsif $c.lines.elems != 1 {
        die "id -u -n returned something unexpected:\n" ~ $c.lines.join("\n") ~ "\n";
    say "Got my username: " ~ $c.lines[0];

    sub fail($r, @cmd) {
        die "fail with exit code $r.exitcode() and $r.lines().elems() " ~
            "line(s) of output and cmd " ~ @cmd;

    $c .= capture-check(:accept(0, 3), 'sh', '-c', 'date');
    say "The current date is $c.lines()[0]" if $c.exitcode == 0;

    $c .= capture-check(:accept(0, 3), 'sh', '-c', 'date; exit 3');
    say "The current date is $c.lines()[0]" if $c.exitcode == 3;

    $c .= capture-check(:accept(0, 3), :&fail, 'sh', '-c', 'date; exit 1');
    say 'not reached, fail() dies';

    $c .= capture-check('git', 'ls-files', '-z', :nl("\0"));
    say 'Got some unquoted filenames from Git:';

    $c .= capture-check('env', 'LANG=fr_FR.ISO-8859-1', 'date', :enc('ISO-8859-1'));


This class provides two methods to execute an external command, capture its output and exit code, and, in capture-check(), raise an error on unexpected exit code values.


  • exitcode

    Int:D $.exitcode

    The exit code of the executed external command.

  • lines

    Str:D @.lines

    The output of the external command split into lines with the newline terminator removed.


  • method capture()

    method capture(*@cmd, Str :$enc, Str :$nl)

    Execute the specified command in the same way as run() would, then create a new Shell::Capture object with its exitcode and lines members set respectively to the exit code of the command and its output split into lines, as described above.

    The $enc and $nl parameters, if supplied, are passed directly to run(), allowing the caller to specify the encoding of the data output by the external program and the character (or string) used to delimit lines in the output. See the Proc.new() documentation for more information.

  • method capture-check()

    method capture-check(:$accept, :$fail, Str :$enc, Str :$nl, *@cmd)

    Execute the specified command and create a Shell::Capture object in the same way as capture(), then check the exit code against the $accept list (default: only 0). If the exit code is on the list, return the Shell::Capture object to the caller.

    If the exit code is not on the list and there is no $fail handler specified, output an error message to the standard error stream and terminate the program. If a fail handler is specified, invoke it with two arguments: the Shell::Capture object for further examination and the command executed; if the fail handler returns, capture-check() will return the Shell::Capture object to its caller (useful for writing tests).

    The $enc and $nl parameters, if specified, are passed directly to run() just as in capture().


Peter Pentchev <roam@ringlet.net>


Copyright (C) 2016, 2017 Peter Pentchev


The Shell::Capture module is distributed under the terms of the Artistic License 2.0. For more details, see the full text of the license in the file LICENSE in the source distribution.