my $bar = baz(); if ($@) { die "baz failed!\n"; }

Yeah, don't do that. That isn't a feature of Perl that is discarding the error reason. That is bad coding that is explicitly discarding the error reason. Such code should look at least more like:

my $bar = baz(); if ($@) { die "baz failed: $@\n"; } # ^^^^

The feature of (modern) Perl that could discard an error reason goes more like this:

#!/usr/bin/perl use strict; { package Deal; sub new { bless {} } sub make { "No collateral" } sub free_resources { unlink $_[0]->{tmp} } sub DESTROY { my( $self ) = @_; $self->free_resources() or die "Failed to free resources: $!\n"; } } eval { my $deal = Deal->new(); die "Can't make a deal: $_\n" for $deal->make(); 1 } or do { warn "Deal failed: $@\n"; settle(); }; sub settle { # ... }

Which produces:

Deal failed: Can't make a deal: No collateral

But all you have to do is add "-w" (such as to the "#!" line) to get:

Use of uninitialized value in unlink at - line 7. (in cleanup) Failed to free resources: No such file or directory Deal failed: Can't make a deal: No collateral

But, yes, you lose programmatic access to inner error(s).

But if you want programmatic access to errors, then you should be using structured exceptions and you get access to the inner error by having the outer exception store a reference to the inner exception.

If you ever use eval, when it fails, you need to do at least one of the following things with the resulting value of $@:

  1. Log it (such as via warn)
  2. Rethrow it (via die), usually decorated with more context info
  3. Precisely match it and handle it (and probably still log something)

Note that (3) is usually better done using structured exceptions or something like Errno.

We actually have a __DIE__ handler (at $work) in order to log why the program is about to exit (we don't just redirect STDERR straight to the log file as we prefer log lines to be in a parsable format and to include a precise timestamp and some context information). Unfortunately, our old version of Perl has a bug with $^S so we can't reliably distinguish between exceptions that are about to be caught from exceptions that are about to cause the program to exit.

So, for now, we have a flawed heuristic where exceptions that happen within a short time span of the program exiting are logged. I can tell you that it is easily very annoying to have caught exceptions being logged. Having a bunch of fatal-looking error messages that don't actually indicate any kind of problem sucks.

I don't see any way for your idea of collecting all exceptions to produce more signal than noise.

Actually, I don't even see how such an idea ever allows for an exception to be freed. So catching an exception just becomes a memory leak.

- tye        


In reply to Re: eval error stack (noise) by tye
in thread eval error stack by shmem

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.