File Coverage

lib/MooseX/DIC/Configuration/YAML.pm
Criterion Covered Total %
statement 71 72 98.6
branch 14 16 87.5
condition 3 3 100.0
subroutine 15 16 93.7
pod 0 4 0.0
total 103 111 92.7


line stmt bran cond sub pod time code
1             package MooseX::DIC::Configuration::YAML;
2              
3 5     5   2683 use Moose;
  5         14  
  5         40  
4             with 'MooseX::DIC::Configuration';
5              
6 5     5   44976 use YAML::XS;
  5         13857  
  5         390  
7 5     5   1811 use File::Spec::Functions qw/splitpath rel2abs/;
  5         4581  
  5         402  
8 5     5   47 use File::Slurper 'read_binary';
  5         14  
  5         244  
9 5     5   35 use Try::Tiny;
  5         13  
  5         322  
10 5     5   2041 use MooseX::DIC::Configuration::Scanner::FileConfig 'fetch_config_files_from_path';
  5         19  
  5         374  
11 5     5   44 use aliased 'MooseX::DIC::ContainerConfigurationException';
  5         16  
  5         129  
12 5     5   1130 use aliased 'MooseX::DIC::Configuration::ServiceMetadata';
  5         14  
  5         31  
13 5     5   2944 use MooseX::DIC::Configuration::ServiceMetadata::Dependency qw/from_attribute from_yaml/;
  5         30  
  5         44  
14 5     5   3191 use Module::Load 'load';
  5         17  
  5         54  
15              
16             sub get_services_metadata_from_path {
17 8     8 0 33 my ($self,$paths) = @_;
18              
19             return
20 8         48 map { build_services_metadata_from_config_file($_) }
  3         21  
21             fetch_config_files_from_path($paths);
22             }
23              
24             sub build_services_metadata_from_config_file {
25 4     4 0 15 my ($config_file) = @_;
26              
27 4 50       73 ContainerConfigurationException->throw(message=>"Specified config file $config_file not found")
28             unless -f $config_file;
29              
30             # Parse YAML config file
31 4         16 my $raw_config;
32             try {
33 4     4   293 my $config_content = read_binary($config_file);
34 4         608 $raw_config = Load $config_content;
35             } catch {
36 0     0   0 ContainerConfigurationException->throw(message=>"Error while loading config file $config_file: $_");
37 4         51 };
38              
39             # Load included files, to be applied later
40 4         111 my @included_files = ();
41 4 100       25 push @included_files,@{$raw_config->{include}} if exists($raw_config->{include});
  1         5  
42              
43 4         13 my @services_metadata = ();
44 4         12 while(my ($interface,$implementators) = each(%{$raw_config->{mappings}})) {
  9         69  
45              
46             #Make sure the interface package is loaded
47 5         35 load $interface;
48              
49             # The config specs allows the implementators of an interface to be specified
50             # either as a string which defines a simple implementator with default values,
51             # or as a hash of full implementators wich are key-value service metadata
52             # definitions.
53              
54 5 100       39876 if(ref($implementators) eq 'HASH') {
55 4         49 while( my ($implementator,$definition) = each(%$implementators)) {
56              
57             # Make sure the implementator package is loaded
58 4         25 load $implementator;
59              
60 4         51675 my %dependencies = build_dependencies_for($implementator,$definition);
61              
62             my $service_metadata = ServiceMetadata->new(
63             class_name => $implementator,
64             implements => $interface,
65             (exists($definition->{scope})? (scope => $definition->{scope}):()),
66             (exists($definition->{builder})? (builder => $definition->{builder}):()),
67             (exists($definition->{environment})? (environment => $definition->{environment}):()),
68 4 100       291 (exists($definition->{qualifiers})? (qualifiers => $definition->{qualifiers}):()),
    100          
    100          
    50          
69             dependencies => \%dependencies
70             );
71 4         38 push @services_metadata, $service_metadata;
72             }
73             } else {
74             # Make sure the implementator package is loaded
75 1         7 load $implementators;
76              
77 1         17319 my %dependencies = build_dependencies_for($implementators);
78              
79 1         63 my $service_metadata = ServiceMetadata->new(
80             class_name => $implementators,
81             implements => $interface,
82             dependencies => \%dependencies
83             );
84 1         8 push @services_metadata, $service_metadata;
85             }
86              
87             }
88              
89             # Load include files
90             push @services_metadata,
91 1         52 map { build_services_metadata_from_config_file($_) }
92 4         19 map { normalize_included_file_path($config_file,$_) }
  1         5  
93             @included_files;
94              
95 4         46 return @services_metadata;
96             }
97              
98             sub build_dependencies_for {
99 5     5 0 23 my ($package,$definition) = @_;
100              
101             my %dependencies =
102 5         33 map {( $_->name => from_attribute($_) ) }
  2         192  
103             $package->meta->get_all_attributes;
104              
105             # Override the dependency metadata found in the class with specific config
106 5 100 100     275 if(defined($definition) and exists($definition->{dependencies})){
107 1         4 while(my ($dependency,$dependency_definition) = each(%{$definition->{dependencies}})) {
  2         16  
108 1         8 $dependencies{$dependency} = from_yaml($dependency,$dependency_definition);
109             }
110             }
111              
112 5         25 return %dependencies;
113              
114             }
115              
116             sub normalize_included_file_path {
117 1     1 0 5 my ($original_file,$included_file) = @_;
118 1         7 my ($volume,$path,$file) = splitpath($original_file);
119              
120 1         26 return rel2abs($included_file,$path);
121             }
122              
123             1;