File Coverage

blib/lib/MooX/ValidateSubs/Role.pm
Criterion Covered Total %
statement 67 67 100.0
branch 29 30 96.6
condition 28 38 73.6
subroutine 8 8 100.0
pod n/a
total 132 143 92.3


line stmt bran cond sub pod time code
1             package MooX::ValidateSubs::Role;
2              
3 10     10   151275 use Moo::Role;
  10         25  
  10         55  
4 10     10   3324 use Carp qw/croak/;
  10         23  
  10         525  
5 10     10   4519 use Type::Utils qw//;
  10         265151  
  10         385  
6 10     10   5410 use Type::Params qw/compile compile_named/;
  10         526320  
  10         100  
7 10     10   3023 use Types::Standard qw//;
  10         23  
  10         6312  
8              
9             sub _validate_sub {
10 76     76   229 my ( $self, $name, $type, $spec, @params ) = @_;
11 76         278 my $store_spec = sprintf '%s_spec', $name;
12              
13 76   66     343 my $compiled_check = ($self->$store_spec->{"compiled_$type"} ||= do {
14 28 100       107 if (ref $spec eq 'ARRAY') {
15             my @types = map {
16 12         32 my ($constraint, $default) = (@$_, 0);
  33         1016  
17 33 100       120 $default eq '1' ? Types::Standard::Optional->of($constraint) : $constraint;
18             } @$spec;
19 12         131 compile(@types);
20             }
21             else {
22 16         29 my %types;
23 16         66 for my $key (keys %$spec) {
24 56         1981 my ($constraint, $default) = (@{$spec->{$key}}, 0);
  56         126  
25 56 100       169 $types{$key} =
26             $default eq '1' ? Types::Standard::Optional->of($constraint) : $constraint;
27             }
28 16         681 compile_named(%types);
29             }
30             });
31              
32 76         36338 my @count = ( scalar @params );
33 76 100       239 if ( ref $spec eq 'ARRAY' ) {
34 36         54 push @count, scalar @{$spec};
  36         67  
35              
36 36 100 50     49 @params = $self->_preprocess_params(@params) and $count[0] = scalar @params if ( do {
37 36         56 my $preprocess = $count[0];
38 36 100 66     276 $_ == 0 || ! $_ % 2 ? $params[$_] =~ m/[0-9]+/ && $params[$_] <= $count[1] ? next : do { $preprocess = 0 } && last : next foreach 0 .. $count[0] - 1;
    100 100        
      50        
39 36         91 $preprocess;
40             } );
41              
42 36 100 100     112 if ( $count[0] == 1 && $count[1] != 1 and ref $params[0] eq 'ARRAY' ) {
      100        
43 4         8 @params = @{ $params[0] };
  4         11  
44 4         7 $count[0] = scalar @params;
45 4         9 $count[3] = 'ref';
46             }
47              
48 36         87 $count[2] = $count[1] - grep { $spec->[$_]->[1] } 0 .. $count[1] - 1;
  105         173  
49 36 100 66     899 $count[0] >= $count[2] && $count[0] <= $count[1]
50             or croak sprintf 'Error - Invalid count in %s for sub - %s - expected - %s - got - %s',
51             $type, $name, $count[1], $count[0];
52              
53 29         57 foreach ( 0 .. $count[1] - 1 ) {
54 82 50 100     332 not $params[$_] and $spec->[$_]->[1]
      33        
      66        
55             and ( $spec->[$_]->[1] =~ m/^1$/ and next or $params[$_] = $self->_default( $spec->[$_]->[1] ) );
56             }
57              
58 29         91 @params = $compiled_check->(@params);
59 29 100       567 return defined $count[3] ? \@params : @params;
60             }
61              
62 40 100       142 my %para = $count[0] == 1 ? %{ $params[0] } : @params;
  6         25  
63 40         71 my %cry = ( %{$spec}, %para );
  40         168  
64 40         121 foreach ( keys %cry ) {
65             not $para{$_} and $spec->{$_}->[1]
66 139 100 100     669 and ( $spec->{$_}->[1] =~ m/^1$/ and next or $para{$_} = $self->_default( $spec->{$_}->[1] ) );
      33        
      100        
67             }
68              
69 40         158 my $paraRef = $compiled_check->(\%para);
70              
71 28 100       1077 return $count[0] == 1 ? $paraRef : %{$paraRef};
  23         165  
72             }
73              
74             sub _default {
75 80     80   154 my ( $self, $default ) = @_;
76              
77 80 100       179 if ( ref $default eq 'CODE' ) {
78 62         155 return $default->();
79             }
80 18         96 return $self->$default;
81             }
82              
83             sub _preprocess_params {
84 8     8   28 my ($self, %params) = @_;
85              
86 8         14 my @world;
87 8         29 map { $world[$_] = $params{$_} } sort keys %params;
  10         26  
88 8         33 return @world;
89             }
90              
91             1;
92