Link to home
Start Free TrialLog in
Avatar of FishMonger
FishMongerFlag for United States of America

asked on

Handling fatal errors while using HTML::Template

My script makes db and ssh connections to several servers and rather than using 'die' (and CGI::Carp) when/if there is a fatal error, I want to use a sub that assigns one or more template vars then output and exit.  However, I've been unable to get this to work as desired.  If I leave in "use CGI::Carp qw(fatalsToBrowser)", then instead of executing the sub and displaying the error in the template, it produces the standard die error.  If I comment out CGI::Carp, then it returns a blank page.

Here are the relevant portions of the script and template.

my $dbh = DBI->connect("DBI:mysql:$db:$server", $user, $pass,
                         { RaiseError => 1, PrintError => 0 } )
              or fatal($DBI::errstr);

sub fatal {
   my $error = shift;
   $template->param(fatal_error => $error);
   $template->output;
   exit;
}


<!-- container to display fatal error messages -->
<TMPL_IF NAME="fatal_error">
  <div class="status_window">
    <h3>FATAL ERROR</h3>
    <p><TMPL_VAR NAME="fatal_error"></p>
  </div>
</TMPL_IF>
<!-- end of error container -->

I also tried wrapping the db call in an eval block and execute the fatal sub if an error is caught, but received a blank page.

Anyone know the proper way to handle fatal errors cleanly while using HTML::Template?
ASKER CERTIFIED SOLUTION
Avatar of mjcoyne
mjcoyne

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of FishMonger

ASKER

That gave me a compilation error until I realized that it was missing the semi-colon at the end.  Once I added the semi-colon, it returned a blank page.  Actually, the page comes up normally initially, but returns a blank page when I submit the form which does the db query.

However, your suggestion made me take a closer look at it and I found the problem.

$template->output;

should be
print $template->output;
Avatar of mjcoyne
mjcoyne

So, what ultimately worked was:

$SIG{__DIE__} = sub {
   my $error = shift;
   $template->param(fatal_error => $error);
   print $template->output;
   exit;
};

?
Yes, modifying the die handler like that works, but so does my original sub.  The key fix was adding the missing print keyword, which was a dumb mistake on my part.

I'm currently using the modified die handler while I'm in the development stage, however I don't see its advantage over using the fatal sub.  In fact it might have a slight disadvantage (in style only).  I prefer to place all of my subs near the end of the script, but I think the reassignment of the die handler needs to be placed near the top.
I agree, there's likely no benefit because, in this case, the error you're trapping is not fatal from the Perl script's point of view -- the script will continue even if $DBI::errstr is populated.

Thanks for the points anyway...:)
You're welcome :)

One thing I haven't yet figured out is now that we can cross post the questions in multiple areas, which area do the points get applied to?  Did you get these points in Perl or CGI or both?
I asked the same question -- see https://www.experts-exchange.com/questions/22434410/Why-are-so-many-questions-being-reassigned-to-different-topic-areas-recently.html (still not sure of how to use the shorter EE links...).

Apparently, the points are awarded in both areas.