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

Hi,

I have a code which archives the files and create the corresponding zip files with same name. But this piece of code works on some folder correctly , whereas on other it gives error. "Can't call method "desiredCompressionlevel" on an undefined value at C:/Perl64/Archive/Zip/Archive.pm line 261"

sub addFile { my $self = shift; my ( $fileName, $newName, $compressionLevel ); if ( ref( $_[0] ) eq 'HASH' ) { $fileName = $_[0]->{filename}; $newName = $_[0]->{zipName}; $compressionLevel = $_[0]->{compressionLevel}; } else { ( $fileName, $newName, $compressionLevel ) = @_; } if ( $^O eq 'MSWin32' && $Archive::Zip::UNICODE ) { $fileName = Win32::GetANSIPathName($fileName); } my $newMember = $self->ZIPMEMBERCLASS->newFromFile( $fileName, $ne +wName ); $newMember->desiredCompressionLevel($compressionLevel); if ( $self->{'storeSymbolicLink'} && -l $fileName ) { my $newMember = $self->ZIPMEMBERCLASS->newFromString(readlink +$fileName, $newName); # For symbolic links, External File Attribute is set to 0xA1FF +0000 by Info-ZIP $newMember->{'externalFileAttributes'} = 0xA1FF0000; $self->addMember($newMember); } else { $self->addMember($newMember); } if ( $^O eq 'MSWin32' && $Archive::Zip::UNICODE ) { $newMember->{'fileName'} = encode_utf8( Win32::GetLongPathName +($fileName) ); } return $newMember; }

Replies are listed 'Best First'.
Re: Perl Archiving Process error
by Eily (Monsignor) on Jul 12, 2016 at 12:48 UTC

    The error is pretty explicit. $newMember is undef.

    You can either check that the $newMember is defined before calling a method on it: warn "Error while archiving file $fileName to $newName" and return unless defined $newMember
    or catch the error with an eval eval { $newMember->desiredCompressionLevel($compressionLevel); 1; } or warn "Error for file $fileName, $newName : $@" and return;

    eval will return the last instruction (here 1) if it executes correctly or undef if an error is raised. So with the idiom eval { THING; 1; } a true value will be returned on success.

    eval { THING }; warn if $@;
    does the same thing by checking the state of the variable $@.

    Once you have found which file is a problem, you'll have to find out why newFromFile() returns undef in that case.

      > does the same thing

      Not always. See Bug in eval in pre-5.14.

      ($q=q:Sq=~/;[c](.)(.)/;chr(-||-|5+lengthSq)`"S|oS2"`map{chr |+ord }map{substrSq`S_+|`|}3E|-|`7**2-3:)=~y+S|`+$1,++print+eval$q,q,a,

        OK so the eval { BLOCK; 1 } or do { } idiom isn't just about finding the shortest or cutest way to write it. Thanks for the info :)

Re: Perl Archiving Process error
by GotToBTru (Prior) on Jul 12, 2016 at 12:46 UTC

    The problem seems to be not in this routine but in the one that calls it. Make sure the hash you pass as an argument has a value for key 'compressionLevel', or that you are passing 3 arguments.

    But God demonstrates His own love toward us, in that while we were yet sinners, Christ died for us. Romans 5:8 (NASB)