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

Dear Perl Monks,

I just tried to make a simple logger package, having a compilation error with its ver.1 as attached below.

error message

Bareword found where operator expected at /home/tatsu/Perl/MyLog/MyLog +.pm line 36, near "} encode" (Missing operator before encode?) syntax error at /home/tatsu/Perl/MyLog/MyLog.pm line 36, near "} encod +e" Compilation failed in require at logtest.pl line 6. BEGIN failed--compilation aborted at logtest.pl line 6.

MyLog.pm (ver.1)

use utf8; use Time::Piece; use Carp 'croak'; use Encode 'encode'; sub new { my $class = shift; my $self = {}; bless $self, $class; my $timesig = localtime->strftime("%y%m%d%H%M%S"); my $logfile = $timesig . '.log'; if (-f $logfile) { croak "log file ${logfile} already exists.: $!"; } open my $fh, '>>', $logfile or croak "can't open log file ${logfile}.: $!"; $self->{fh} = $fh; return $self; } sub DESTROY { my $self = shift; close $self->{fh}; } sub log { my $self = shift; my $timesig = localtime->strftime("%y%m%d%H%M%S"); # my $fh = $self->{fh}; foreach my $msg (@_) { print $self->{fh} encode('utf8', $timesig . ': ' . $msg . "\n"); # print $fh encode('utf8', $timesig . ': ' . $msg . "\n"); } } 1;

When a local var $fh was used for the file handle with its print command in the log subroutine (ver.2), however, no error occurred and everything worked as expected. It appears that the error occurs with the 'print $self->{fh}' part, but I am not sure how it comes to the error message 'Bareword found where operator expected...'.

Any advice would be much appreciated.

Sincerely,

MyLog.pm (ver.2, log subroutine only)

sub log { my $self = shift; my $timesig = localtime->strftime("%y%m%d%H%M%S"); my $fh = $self->{fh}; foreach my $msg (@_) { # print $self->{fh} encode('utf8', $timesig . ': ' . $msg . "\n"); print $fh encode('utf8', $timesig . ': ' . $msg . "\n"); } } 1;

logtest.pl

use strict; use warnings; use utf8; use FindBin; use lib $FindBin::Bin; use MyLog; my $mylog = MyLog->new(); $mylog->log(); $mylog->log(''); $mylog->log('a', 'b');

Replies are listed 'Best First'.
Re: file handle var for print command
by Corion (Patriarch) on Sep 24, 2025 at 07:29 UTC

    See print:

    If you're storing handles in an array or hash, or in general whenever you're using any expression more complex than a bareword handle or a plain, unsubscripted scalar variable to retrieve it, you will have to use a block returning the filehandle value instead, in which case the LIST may not be omitted:

    So, if you're storing the filehandle in a complex structure, you need the block:

    print { $self->{fh} } encode( ... )
      This also works as expected, but I couldn't find a documented explanation for it:
      $self->{fh}->print("test with print\n");

        Filehandle GLOBs behave like IO::Handle instances (but aren't actually for purposes of inheritance according to the BUGS entry in the IO::Handle docs) so that's just a normal method call to the print method and doesn't get into weird indirect object parsing corners.

        The cake is a lie.
        The cake is a lie.
        The cake is a lie.