File Coverage

blib/lib/Bolts/Role/Initializer.pm
Criterion Covered Total %
statement 5 5 100.0
branch n/a
condition n/a
subroutine 2 2 100.0
pod 1 1 100.0
total 8 8 100.0


line stmt bran cond sub pod time code
1             package Bolts::Role::Initializer;
2             $Bolts::Role::Initializer::VERSION = '0.142930';
3             # ABSTRACT: Give components some control over their destiny
4              
5 8     8   3836 use Moose::Role;
  8         14  
  8         48  
6              
7              
8             requires 'init_locator';
9              
10              
11             sub initialize_value {
12 2     2 1 5 my $self = shift;
13 2         8 return $self->init_locator->acquire(@_);
14             }
15              
16             1;
17              
18             __END__
19              
20             =pod
21              
22             =encoding UTF-8
23              
24             =head1 NAME
25              
26             Bolts::Role::Initializer - Give components some control over their destiny
27              
28             =head1 VERSION
29              
30             version 0.142930
31              
32             =head1 SYNOPSIS
33              
34             package MyApp::Thing;
35             use Moose;
36              
37             use MyApp::Bag;
38              
39             has init_locator => (
40             is => 'rw',
41             does => 'Bolts::Role::Locator',
42             lazy => 1,
43             builder => '_build_init_locator',
44             );
45              
46             sub _build_init_locator { MyApp::Bag->new }
47              
48             with 'Bolts::Role::Initializer';
49              
50             has foo => (
51             is => 'rw',
52             isa => 'MyApp::Foo',
53             traits => [ 'Bolts::Initializer' ],
54             );
55              
56             # Later...
57             use Bolts::Util qw( bolts_init );
58             my $thing = MyApp::Thing->new(
59             foo => bolts_init('path', 'to', 'foo'),
60             );
61              
62             =head1 DESCRIPTION
63              
64             While IOC provides an elegant way to decouple your objects and such, it is sometimes convenient to give objects more control over their setup. This role grants your class a special initializer method that can be used by initializer attributes, which can automatically find their values using an associated L<Bolts::Role::Locator> object.
65              
66             For example, it can take a call like this:
67              
68             my $thing = MyApp::Thing->new(
69             foo => $locator->acquire('path', 'to', 'foo'),
70             );
71              
72             to this:
73              
74             my $thing = MyApp::Thing->new(
75             foo => bolts_init('path', 'to', 'foo'),
76             );
77              
78             The caller no longer has to know anything about the C<$locator>, just a common path within. Perhaps an even better way would be to move the initialization of MyApp::Thing into the locator to manage it's life cycle, scope, etc., but sometimes this is more convenient or practical or even possible.
79              
80             Any attribute you want to have initialized this way should be tagged with the C<Bolts::Initializer> trait, which is defined in L<Bolts::Meta::Attribute::Trait::Initializer>. This trait modifies the attribute so that it may be initialized either by the actual value without an initializer or by looking up a value within the L</init_locator> of the object if given an initializer (a L<Bolts::Meta::Initializer> object, usually gotten by calling L<Bolts::Util/bolts_init>).
81              
82             B<Caution:> This is slightly messy with bits and pieces spread out a bit more than I like. I might reorganize these pieces a bit in the future if I can find a better way to do it.
83              
84             =head1 REQUIRED METHODS
85              
86             =head2 init_locator
87              
88             my $locator = $self->init_locator;
89              
90             This method takes no arguments and must return an object that does L<Bolts::Role::Locator>.
91              
92             =head1 METHODS
93              
94             =head2 initialize_value
95              
96             my $value = $self->initialize_value(@path, \%params);
97              
98             This is used to perform acquisition with the initializer object. This is just delegated to the C<acquire> method of L</init_locator>.
99              
100             =head1 AUTHOR
101              
102             Andrew Sterling Hanenkamp <hanenkamp@cpan.org>
103              
104             =head1 COPYRIGHT AND LICENSE
105              
106             This software is copyright (c) 2014 by Qubling Software LLC.
107              
108             This is free software; you can redistribute it and/or modify it under
109             the same terms as the Perl 5 programming language system itself.
110              
111             =cut