File Coverage

blib/lib/Sub/Meta/Param.pm
Criterion Covered Total %
statement 121 121 100.0
branch 68 68 100.0
condition 18 18 100.0
subroutine 33 33 100.0
pod 28 28 100.0
total 268 268 100.0


line stmt bran cond sub pod time code
1             package Sub::Meta::Param;
2 36     36   2617000 use 5.010;
  36         201  
3 36     36   182 use strict;
  36         65  
  36         879  
4 36     36   185 use warnings;
  36         68  
  36         1972  
5              
6             our $VERSION = "0.13";
7              
8 36     36   248 use Scalar::Util ();
  36         83  
  36         1572  
9              
10             use overload
11 36         398 fallback => 1,
12             eq => \&is_same_interface,
13 36     36   266 ;
  36         67  
14              
15             my %DEFAULT = ( named => 0, optional => 0, invocant => 0 );
16              
17             sub new {
18 215     215 1 148803 my ($class, @args) = @_;
19 215         354 my $v = $args[0];
20 215 100 100     925 my %args = @args == 1 ? ref $v && (ref $v eq 'HASH') ? %{$v}
  75 100       337  
21             : ( type => $v )
22             : @args;
23              
24 215 100       599 $args{optional} = !delete $args{required} if exists $args{required};
25 215 100       460 $args{named} = !delete $args{positional} if exists $args{positional};
26 215 100       424 $args{type} = delete $args{isa} if exists $args{isa};
27              
28 215         925 %args = (%DEFAULT, %args);
29              
30 215         1202 return bless \%args => $class;
31             }
32              
33 232   100 232 1 36843 sub name() { my $self = shift; return $self->{name} // '' }
  232         1446  
34 554     554 1 22508 sub type() { my $self = shift; return $self->{type} }
  554         3337  
35 61     61 1 9894 sub default() { my $self = shift; return $self->{default} } ## no critic (ProhibitBuiltinHomonyms)
  61         147  
36 61     61 1 9595 sub coerce() { my $self = shift; return $self->{coerce} }
  61         136  
37 543     543 1 11530 sub optional() { my $self = shift; return !!$self->{optional} }
  543         3641  
38 144     144 1 11655 sub required() { my $self = shift; return !$self->{optional} }
  144         526  
39 642     642 1 12334 sub named() { my $self = shift; return !!$self->{named} }
  642         2653  
40 217     217 1 11532 sub positional() { my $self = shift; return !$self->{named} }
  217         776  
41 61     61 1 11277 sub invocant() { my $self = shift; return !!$self->{invocant} }
  61         162  
42              
43 449     449 1 12006 sub has_name() { my $self = shift; return defined $self->{name} }
  449         2353  
44 334     334 1 11638 sub has_type() { my $self = shift; return defined $self->{type} }
  334         1274  
45 61     61 1 11275 sub has_default() { my $self = shift; return defined $self->{default} }
  61         157  
46 61     61 1 11314 sub has_coerce() { my $self = shift; return defined $self->{coerce} }
  61         174  
47              
48 3     3 1 9969 sub set_name { my ($self, $v) = @_; $self->{name} = $v; return $self }
  3         39  
  3         17  
49 4     4 1 11643 sub set_type { my ($self, $v) = @_; $self->{type} = $v; return $self }
  4         33  
  4         28  
50 4     4 1 11336 sub set_default { my ($self, $v) = @_; $self->{default} = $v; return $self }
  4         35  
  4         29  
51 4     4 1 11615 sub set_coerce { my ($self, $v) = @_; $self->{coerce} = $v; return $self }
  4         33  
  4         26  
52 6 100   6 1 7994 sub set_optional { my ($self, $v) = @_; $self->{optional} = !!(defined $v ? $v : 1); return $self }
  6         46  
  6         30  
53 6 100   6 1 8398 sub set_required { my ($self, $v) = @_; $self->{optional} = !(defined $v ? $v : 1); return $self }
  6         19  
  6         28  
54 6 100   6 1 8449 sub set_named { my ($self, $v) = @_; $self->{named} = !!(defined $v ? $v : 1); return $self }
  6         53  
  6         33  
55 6 100   6 1 8031 sub set_positional { my ($self, $v) = @_; $self->{named} = !(defined $v ? $v : 1); return $self }
  6         21  
  6         26  
56 58 100   58 1 18062 sub set_invocant { my ($self, $v) = @_; $self->{invocant} = !!(defined $v ? $v : 1); return $self }
  58         268  
  58         143  
57              
58             # alias
59             sub isa_() :method; # NOT isa
60             *isa_ = \&type;
61              
62             sub set_isa;
63             *set_isa = \&set_type;
64              
65             sub is_same_interface {
66 113     113 1 238 my ($self, $other) = @_;
67              
68 113 100 100     706 return unless Scalar::Util::blessed($other) && $other->isa('Sub::Meta::Param');
69              
70 103 100       267 if ($self->has_name) {
71 16 100       40 return unless $self->name eq $other->name
72             }
73             else {
74 87 100       148 return if $other->has_name
75             }
76              
77 93 100       193 if ($self->has_type) {
78 66 100 100     121 return unless $self->type eq ($other->type // '');
79             }
80             else {
81 27 100       56 return if $other->has_type
82             }
83              
84 71 100       160 return unless $self->optional eq $other->optional;
85              
86 66 100       140 return unless $self->named eq $other->named;
87              
88 61         219 return !!1;
89             }
90              
91             sub is_relaxed_same_interface {
92 94     94 1 176 my ($self, $other) = @_;
93              
94 94 100 100     464 return unless Scalar::Util::blessed($other) && $other->isa('Sub::Meta::Param');
95              
96 92 100       209 if ($self->has_name) {
97 14 100       28 return unless $self->name eq $other->name
98             }
99              
100 87 100       164 if ($self->has_type) {
101 55 100 100     105 return unless $self->type eq ($other->type // '');
102             }
103              
104 69 100       136 return unless $self->optional eq $other->optional;
105              
106 64 100       172 return unless $self->named eq $other->named;
107              
108 59         518 return !!1;
109             }
110              
111             sub is_same_interface_inlined {
112 21     21 1 49 my ($self, $v) = @_;
113              
114 21         32 my @src;
115 21         83 push @src => sprintf("Scalar::Util::blessed(%s) && %s->isa('Sub::Meta::Param')", $v, $v);
116              
117 21 100       55 push @src => $self->has_name ? sprintf("'%s' eq %s->name", $self->name, $v)
118             : sprintf('!%s->has_name', $v);
119              
120 21 100       59 push @src => $self->has_type ? sprintf("'%s' eq (%s->type // '')", "@{[$self->type]}", $v)
  13         33  
121             : sprintf('!%s->has_type', $v);
122              
123 21         63 push @src => sprintf("'%s' eq %s->optional", $self->optional, $v);
124              
125 21         57 push @src => sprintf("'%s' eq %s->named", $self->named, $v);
126              
127 21         1268 return join "\n && ", @src;
128             }
129              
130             sub is_relaxed_same_interface_inlined {
131 21     21 1 60 my ($self, $v) = @_;
132              
133 21         33 my @src;
134 21         75 push @src => sprintf("Scalar::Util::blessed(%s) && %s->isa('Sub::Meta::Param')", $v, $v);
135              
136 21 100       45 push @src => sprintf("'%s' eq %s->name", $self->name, $v) if $self->has_name;
137              
138 21 100       53 push @src => sprintf("'%s' eq (%s->type // '')", "@{[$self->type]}", $v) if $self->has_type;
  13         29  
139              
140 21         59 push @src => sprintf("'%s' eq %s->optional", $self->optional, $v);
141              
142 21         63 push @src => sprintf("'%s' eq %s->named", $self->named, $v);
143              
144 21         835 return join "\n && ", @src;
145             }
146              
147             sub display {
148 36     36 1 49 my $self = shift;
149              
150 36         48 my $s = '';
151 36 100       62 $s .= $self->type if $self->type;
152 36 100 100     101 $s .= ' ' if $s && $self->name;
153 36 100       78 $s .= ':' if $self->named;
154 36 100       70 $s .= $self->name if $self->name;
155 36         146 return $s;
156             }
157              
158              
159             1;
160             __END__