in reply to File Handle questions

G'day demichi,

Declaring LOG_FH should, I think, fix both your posted problems.

You'll then find another problem with your $log_fh assignment. You need to assign a globref:

#my $log_fh = *LOG_FH; my $log_fh = \*LOG_FH;

To be honest, I don't know why you're even bothering with that globally-scoped package variable. Why not just:

my $log_fh; LOG_MSG_OPEN($log_fh,$logfile);

Recomendations:

Update: Expanded the "Names with all uppercase characters ..." point.

— Ken

Replies are listed 'Best First'.
Re^2: File Handle questions
by demichi (Beadle) on Oct 23, 2016 at 15:30 UTC
    Hi,

    this

    my $log_fh = \*LOG_FH;

    does not help as I get the same errors. But returning the FH in the sub works :)

    my $log_fh; # = \*LOG_FH; $log_fh = LOG_MSG_OPEN($log_fh,$logfile); LOG_MSG($log_fh,$vbse,"v",$lglvl,5,"GENERAL","Starting Script $0"); ... module ... sub LOG_MSG_OPEN { my $par_fh = $_[0]; my $par_filepath = $_[1]; open($par_fh,"> $par_filepath") or die ("Can't open $par_filepath: + $!\n"); $par_fh->autoflush(1); return *$par_fh; } sub LOG_MSG { my $par_fh = shift (@_); ... print $par_fh "$logdate,$logtime,$SEV_KEYWORD,$par_FUNCTION,@line\ +n"; }

    Thanks for your other recommendations. I always used uppercase fos my subs. I will check the open and autodie. Kind regards, de Michi

      "... my $log_fh = \*LOG_FH; does not help as I get the same errors."

      I suggested declaring LOG_FH to "fix both your posted problems".

      Using the globref, \*LOG_FH, was to handle an anticipated, subsequent problem.

      — Ken

Re^2: File Handle questions
by demichi (Beadle) on Oct 23, 2016 at 16:25 UTC

    It looks like autodie is a very good idea. Can you give me an example how I can use my function (for logging) with autodie as I do it with die?

    With die:

    unlink $filename or die LOG_MSG($par_lglvl,3,"DOUPGRADE","Could not de +lete $filename: $!");
    Thanks.
      $ cat ad.pl #!/usr/bin/env perl use strict; use warnings; use autodie; unlink ('filewhichdoesnotexist'); print "Everything went fine.\n"; $ ./ad.pl Can't unlink('filewhichdoesnotexist'): No such file or directory at ./ +ad.pl line 6 $

      So you can simply redirect STDERR to the logfile of your choosing.

      Looking at autodie, it seems to not be easy to use with logging - other than redirecting STDERR in to your log file. Also, it doesn't seem to have a hook for providing a function for custom formatting.

      You could try using an END block to log the error after something dies.

      You could set up a $SIG{__DIE_} handler (see %SIG) to intercept the error and call your log function. HOWEVER, $SIG{__DIE_} handlers are called even when die is called inside an eval, so can be messy to get working correctly.

      Maybe overriding CORE::GLOBAL::die() would work for your purpose.

      You could follow the examples in autodie to "trap" the die with eval, then examine $@ to determine whether and what to log.

      In your case, I'd say either redirect STDERR to your log file, or use die LOG_MSG(...); the way you are, now.