File Coverage

lib/Peco/Spec.pm
Criterion Covered Total %
statement 67 94 71.2
branch 5 18 27.7
condition 1 3 33.3
subroutine 21 28 75.0
pod 0 4 0.0
total 94 147 63.9


line stmt bran cond sub pod time code
1             package Peco::Spec;
2              
3 7     7   24299 use strict;
  7         14  
  7         211  
4 7     7   32 use warnings;
  7         13  
  7         196  
5              
6 7     7   33 use Carp qw/croak/;
  7         12  
  7         4144  
7              
8 0     0 0 0 sub new { bless { } }
9              
10 0     0 0 0 sub class { }
11              
12 0     0 0 0 sub instance { }
13              
14             sub clone {
15 0     0 0 0 my ( $self, $data ) = @_;
16 0         0 my $copy = ref( $self )->new(
17             $self->{class}, $self->{deps}, $self->{ctor}, $self->{attrs}
18             );
19 0 0       0 $copy->{instance} = $self->{instance} if $data;
20 0         0 return $copy;
21             }
22              
23             sub _create {
24 7     7   20 my ( $self, $cntr, %seen ) = @_;
25              
26 7         45 my @args = $self->_resolve( $cntr, %seen );
27 4         7 my $ctor = $self->{ctor};
28              
29 4 50       815 $self->{class}->can( $ctor ) || croak( "$self->{class} can't `$ctor'" );
30              
31 0         0 my $inst = $self->{class}->$ctor( @args );
32 0         0 while ( my ( $k, $v ) = each %{ $self->{attrs} } ) {
  0         0  
33 0 0       0 $inst->$k( $v ) if $inst->can( $k );
34             }
35              
36 0         0 return $inst;
37             }
38              
39             sub _resolve {
40 7     7   18 my ( $self, $cntr, %seen ) = @_;
41              
42 7 50       26 if ( ref $self->{deps} eq 'ARRAY' ) {
    0          
43 7         9 my @resolved;
44 7         10 foreach my $k ( @{ $self->{deps} } ) {
  7         20  
45 4 50       10 if ( ref $k ) {
46 0         0 push @resolved, $$k;
47 0         0 next;
48             }
49 4 100       303 croak( "cyclic dependency detected for $k" ) if $seen{ $k };
50 3         18 push @resolved, $cntr->service( $k, %seen );
51             }
52 4         16 return @resolved;
53             }
54             elsif ( ref $self->{deps} eq 'HASH' ) {
55 0         0 my %resolved;
56 0         0 foreach my $k ( keys %{ $self->{deps} } ) {
  0         0  
57 0 0       0 if ( ref $self->{deps}{ $k } ) {
58 0         0 $resolved{ $k } = ${ $self->{deps}{ $k } };
  0         0  
59 0         0 next;
60             }
61 0 0       0 croak( "cyclic dependency detected for $k" ) if $seen{$k};
62 0         0 $resolved{ $k } = $cntr->service( $self->{deps}{ $k }, %seen );
63             }
64 0         0 return %resolved;
65             }
66             }
67              
68              
69             package Peco::Spec::Class;
70              
71 7     7   40 use strict;
  7         8  
  7         201  
72 7     7   42 use warnings;
  7         17  
  7         250  
73              
74 7     7   32 use Carp qw/croak/;
  7         11  
  7         279  
75 7     7   38 use base qw/Peco::Spec/;
  7         17  
  7         1825  
76              
77             sub new {
78 7     7   23 my ( $class, @spec ) = @_;
79 7         36 my $self = bless {
80             class => $spec[0],
81             deps => $spec[1],
82             ctor => $spec[2],
83             attrs => $spec[3],
84             }, $class;
85 7         24 $self;
86             }
87              
88 0     0   0 sub class { shift->{class} }
89              
90             sub instance {
91 7     7   18 my ( $self, $cntr, $key, %seen ) = @_;
92 7         15 $seen{ $key }++;
93 7   33     112 $self->{instance} ||= $self->_create( $cntr, %seen );
94             }
95              
96              
97             package Peco::Spec::Code;
98              
99 7     7   37 use strict;
  7         10  
  7         214  
100 7     7   31 use warnings;
  7         14  
  7         194  
101              
102 7     7   41 use base qw/Peco::Spec/;
  7         11  
  7         1133  
103              
104             sub new {
105 2     2   3 my ( $class, $code ) = @_;
106 2         6 bless $code, $class;
107             }
108              
109 0     0   0 sub class { ref( $_[0] ) }
110              
111             sub instance {
112 4     4   9 my ( $self, $cntr, $key, %seen ) = @_;
113 4         4 $seen{ $key }++;
114 4         12 return $self->( $cntr );
115             }
116              
117              
118             package Peco::Spec::Const;
119              
120 7     7   31 use strict;
  7         12  
  7         211  
121 7     7   31 use warnings;
  7         11  
  7         202  
122              
123 7     7   28 use base qw/Peco::Spec/;
  7         12  
  7         1003  
124              
125             sub new {
126 3     3   5 my ( $class, $value ) = @_;
127 3         12 bless \$value, $class;
128             }
129              
130 0     0   0 sub class { ref( $_[0] ) }
131 5     5   6 sub instance { ${$_[0]} }
  5         40  
132              
133              
134             1;