-
-
Notifications
You must be signed in to change notification settings - Fork 48
Description
I'm assuming I'm doing something horribly wrong, but here's a tiny type library (I've tried to pare it down to a minimal test case). Note that the YAMLBool
type coerces true
and false
to 1
and 0
, respectively:
package MyTypes {
use Type::Library -base, -declare => qw(
YAMLBool
);
use Type::Params 'compile';
use Type::Utils -all;
use Types::Standard qw(Bool Enum Dict Optional HashRef);
our @EXPORT_OK = 'compile';
BEGIN {
extends qw(
Types::Standard
Types::Common::Numeric
Types::Common::String
);
}
declare '_TrueFalse', as Enum [qw/true false/];
declare 'YAMLBool', as Bool;
coerce 'YAMLBool',
from '_TrueFalse', via { 'true' eq $_ ? 1 : 0 };
}
1;
And here's a program that succeeds:
use 5.26.0;
use warnings;
use lib '.';
use MyTypes qw/Dict YAMLBool Optional HashRef compile/;
my $check = compile(
Dict [
maybe_true => YAMLBool,
not_a_hashref => Optional [HashRef],
]
);
my $minimal = {
maybe_true => 'true',
not_a_hashref => {},
};
$check->($minimal);
But as soon as I change the not_a_hashref
value to a string, I get the following error:
Reference {"maybe_true" => "true","not_a_hashref" => "asdf"} did not pass type constraint "Dict[maybe_true=>YAMLBool,not_a_hashref=>Optional[HashRef]]" (in $_[0]) at fail.pl line 18
Reference {"maybe_true" => "true","not_a_hashref" => "asdf"} did not pass type constraint "Dict[maybe_true=>YAMLBool,not_a_hashref=>Optional[HashRef]]" (in $_[0])
"Dict[maybe_true=>YAMLBool,not_a_hashref=>Optional[HashRef]]" constrains value at key "maybe_true" of hash with "YAMLBool"
"YAMLBool" is a subtype of "Bool"
Value "true" did not pass type constraint "Bool" (in $_[0]->{"maybe_true"})
"Bool" is defined as: (!ref $_ and (!defined $_ or $_ eq q() or $_ eq '0' or $_ eq '1'))
So we see the coercion is valid. However, as soon as I change something other than the coerced value to an invalid state, the coercion doesn't happen and this otherwise valid value is reported as being the source of the problem. The actual type I compiled was about 40 lines long, so this was rather hard to chase down.
- Types::Standard version 1.012001
- Perl 5.26.2
I've also had this happen on Linux boxes with newer Perls and older versions of Types::Standard (1.010006), so it appears that I can reliably produce it.