[Koha-bugs] [Bug 25491] Perl warning at the login page of installer
bugzilla-daemon at bugs.koha-community.org
bugzilla-daemon at bugs.koha-community.org
Wed Jun 17 20:54:17 CEST 2020
https://bugs.koha-community.org/bugzilla3/show_bug.cgi?id=25491
--- Comment #3 from Andrew Nugged <nugged at gmail.com> ---
If we talk about:
if ( $info{'invalid_username_or_password'} &&
$info{'invalid_username_or_password'} == 1) { ...
so this is ok,
there is first-level key check, not a sub-key, so no autovivification
and at the same time, this combines both "existence of the key" check + "Perl
false" check (i.e. undef too) on the left "&&" part.
Autovivification happens for parent keys or array elements in complex data
structures if we will go for a subkey from a key, because Perl first needs to
create all chain or parent structure/refs (autovivification here) to reach the
deepest requested one, but that deepest-requested one does not created.
So for the top-level key it is ok to check existence + Perl non-false in single
"$hash{key}" form.
( docs references:
[https://perldoc.perl.org/perlref.html] "Before this statement, $array[$x]
may have been undefined. If so, it's automatically defined with a hash
reference so that we can look up {"foo"} in it. Likewise $array[$x]->{"foo"}
will automatically get defined with an array reference so that we can look
up [0] in it. This process is called autovivification."
brian d foy's:
https://www.effectiveperlprogramming.com/2011/04/understand-autovivification/
my own example (Peter & Salava, pls pay attention too):
# this is okay, no autovivification and also this prevents "undef" warning:
if ($info{invalid_username_or_password} &&
$info{invalid_username_or_password} == 1) { ...
# this below one is useless, because still no undef-proteciton,
# so warning etmitted in case key has undef:
if (exists $info{invalid_username_or_password} &&
$info{invalid_username_or_password} == 1) { ...
# this is overreaction yet will work correctly:
if (exists $info{invalid_username_or_password} &&
defined $info{invalid_username_or_password} &&
$info{invalid_username_or_password} == 1) { ...
# this is bad, upper level key (config_set) autovivified:
if ($info{config_set}{invalid_username_or_password} &&
$info{config_set}{invalid_username_or_password} == 1) { ...
# this is bad, upper level key (config_set) autovivified, even you have
# 'exists', because before 'exists' Perl solves sub-hash deref:
if (exists $info{config_set}{invalid_username_or_password} &&
$info{config_set}{invalid_username_or_password} == 1) { ...
)
P.S. sorry for such a long example, I wanted all related people to read & train
this and maybe we can refer to this comment one day for my other students :P.
Proof of concept for the local Perl to run & see:
====== vivify.pl ======
#!/usr/bin/env perl
use Modern::Perl; use Data::Dumper qw(Dumper); $|=1; $, = ", ";
$Data::Dumper::Terse = 1; $Data::Dumper::Indent = 0;
my %H = (
user => undef
);
say __LINE__, Dumper \%H;
# 8, {'user' => undef}
# this is okay, no autovivification and also this prevents "undef" warning:
say __LINE__,
$H{user} && $H{user} == 1
? 'User exists, defined, and == 1' : 'User absent';
# 13, User absent
say __LINE__, Dumper \%H;
# 17, {'user' => undef}
# this below one is useless, because still no undef-proteciton,
# so warning etmitted in case key has undef:
say __LINE__,
exists $H{user} && $H{user} == 1
# Use of uninitialized value $H{"user"} in numeric eq (==) at vivify.pl line
23.
? 'User exists and == 1' : 'User absent';
# 22, User absent
say __LINE__, Dumper \%H;
# 27, {'user' => undef}
# this is overreaction yet will work correctly:
say __LINE__,
exists $H{user} && defined $H{user} && $H{user} == 1
? 'User name exists, defined, and == 1' : 'User name absent';
# 32, User name absent
say __LINE__, Dumper \%H;
# 36, {'user' => undef}
%H = ();
say __LINE__, Dumper \%H;
# 41, {}
# this is wrong, upper level key (user) unexpectedly autovivified:
say __LINE__,
$H{user}{name} && $H{user}{name} == 1
? 'User name exists and == 1' : 'User name absent';
# 45, User name absent
say __LINE__, Dumper \%H;
# 49, {'user' => {}}
%H = ();
say __LINE__, Dumper \%H;
# 54, {}
# this is wrong, upper level key (user) unexpectedly autovivified:
say __LINE__,
exists $H{user}{name} && defined $H{user}{name} && $H{user}{name} == 1
? 'User exists and == 1' : 'User absent';
# 58, User absent
say __LINE__, Dumper \%H;
# 62, {'user' => {}}
--
You are receiving this mail because:
You are watching all bug changes.
More information about the Koha-bugs
mailing list