Subject: | Types::Standard: please add $class->DOES(...), $class->isa(...) and $class =~ /$valid_class_re/ constraints. |
Date: | Thu, 02 Jan 2014 20:49:19 +0100 |
To: | bug-Type-Tiny [...] rt.cpan.org |
From: | BPJ <bpj [...] melroch.se> |
Hi,
I'm trying to cook up parameterized constraints similar to
InstanceOf and ConsumerOf but accepting class names rather than
objects as values. I have managed to define them like this, using
the high-level stuff from Type::Utils
for my $belongs_with ( qw[ isa DOES ] ) {
my $name = "Class\u\L$belongs_with";
declare $name, as ClassName, constraint_generator => sub {
return ClassName unless @_;
croak "Param(s) to $name must be valid class name(s)"
if grep { !/$valid_class_re/ } @_;
my @classics = my @classes = @_;
for my $this ( @classics ) {
my $class = $this;
$this = declare as Any,
where { $_->$belongs_with($class) },
display_name => "$name\['$class']";
}
my $classic = @classics > 1
? union( \@classics ) : $classics[0];
local $" = q[', '];
return intersection [ClassName, $classic],
display_name => "$name\['@classes']";
};
}
though I'm sure there are not-so-edgy cases where this wouldn't
suffice. There is some complication in the declaration since I
thought it may be a good idea to not have to check against
ClassName more than once, or does ClassName get checked against
automatically because of being the parent? (BTW it seems the
display_name on the last line never kicks in?)
However I think this may be a common enough need to warrant
making them standard. The same goes for the following, which is
trivial but oft-needed (at least by me) and the regex is a bit
clunky to write.
my $valid_class_re
= qr{ ^ [[:alpha:]] [[:word:]]* (?: :: [[:word:]]+ )* $ }x; #
No /ms !
declare 'ValidClassName' => as StrMatch[$valid_class_re];
Cheers,
/bpj