mcrswan has asked for the wisdom of the Perl Monks concerning the following question:

I have a script which needs to execute unix commands using the backtick operator. I am using the eval function to evaluate and run the unix command, and then I'm doing a Boolean test on $@ to determine if there has been an error. thus eval `$statement`; if($@) {print "error"; ) else {print "statement successful"; } This works when a real error is found, but if I get a simple warning, processing continues down the else leg, as if the statement worked ok. How can I force warnings to be treated as errors, or set $@ to TRUE (or the error value) so I get the error msg for a warning ?

Replies are listed 'Best First'.
Re: trap warnings in $@
by eyepopslikeamosquito (Archbishop) on Feb 26, 2008 at 21:01 UTC

    Why use eval here? To simply run a command and check its return code, I would use something like:

    my $out = `$command`; # $out contains the command stdout my $rc = $? >> 8; # $rc contains command return code

Re: trap warnings in $@
by kyle (Abbot) on Feb 26, 2008 at 21:21 UTC

    I think eval might not be the right tool to use here. In Perl, eval takes a string (or block) of Perl code and executes it. If you put a backtick expression where it's looking for a string, it's going to take the output of the shell command in the backticks and then try to execute it as Perl. Here's a demonstration:

    sub whoops { print "whoops() called\n"; } eval `echo whoops`; print $@ ? "EVAL ERROR: $@\n" : "no error!\n"; eval `echo no_such_sub`; print $@ ? "EVAL ERROR: $@\n" : "no error!\n"; __END__ whoops() called no error! EVAL ERROR: Bareword "no_such_sub" not allowed while "strict subs" in +use at (eval 2) line 1.

    I'm guessing that what you want to do is:

    1. Run an external command.
    2. Get its output.
    3. Find out if it died (gave an abnormal exit status).
    4. Find out also if it spit out a warning (output anything on STDERR).

    I think the responses in Parsing STDERR and STDOUT at the same time might help here. I think that IPC::Run can do all of this, but I haven't used it myself.

Re: trap warnings in $@
by ysth (Canon) on Feb 26, 2008 at 20:46 UTC
    For any warning, $SIG{__WARN__} = sub { die @_ };

    For just perl's internal warnings and registered warnings (which don't seem to have caught on), use warnings FATAL => "all";

Re: trap warnings in $@
by mcrswan (Initiate) on Feb 27, 2008 at 11:39 UTC
    Thanks to all of you for your comments - as you've probably guessed I'm quite a novice at Perl. I've decided to take the easy option, dispense with eval and just capture the return code from $? ...that seems to work a treat....thanks again