Commit | Line | Data |
2336ae0b |
1 | package Catalyst::IOC; |
fb7aaa61 |
2 | use strict; |
3 | use warnings; |
69e61491 |
4 | use Bread::Board qw/depends_on/; |
71d3df94 |
5 | use Catalyst::IOC::ConstructorInjection; |
85ebb635 |
6 | no strict 'refs'; |
2336ae0b |
7 | |
71d3df94 |
8 | use Sub::Exporter -setup => { |
9 | exports => [qw/ |
69e61491 |
10 | depends_on |
71d3df94 |
11 | component |
7cd05fd2 |
12 | model |
9226f304 |
13 | view |
14 | controller |
7cd05fd2 |
15 | container |
71d3df94 |
16 | /], |
17 | groups => { default => [qw/ |
69e61491 |
18 | depends_on |
71d3df94 |
19 | component |
7cd05fd2 |
20 | model |
9226f304 |
21 | view |
22 | controller |
7cd05fd2 |
23 | container |
71d3df94 |
24 | /]}, |
25 | }; |
fddc99a9 |
26 | |
7cd05fd2 |
27 | sub container (&) { |
28 | my $code = shift; |
85ebb635 |
29 | my $caller = caller; |
30 | ${"${caller}::customise_container"} = sub { |
85ebb635 |
31 | local ${"${caller}::current_container"} = shift; |
7cd05fd2 |
32 | $code->(); |
33 | }; |
34 | } |
35 | |
4bb29053 |
36 | sub model (&) { _subcontainer( shift, caller, 'model' ) } |
37 | sub view (&) { _subcontainer( shift, caller, 'view' ) } |
38 | sub controller (&) { _subcontainer( shift, caller, 'controller' ) } |
39 | |
40 | sub _subcontainer (&$$) { |
41 | my ( $code, $caller, $subcontainer ) = @_; |
42 | local ${"${caller}::current_container"} = |
43 | ${"${caller}::current_container"}->get_sub_container($subcontainer); |
7cd05fd2 |
44 | $code->(); |
45 | } |
71d3df94 |
46 | |
4bb29053 |
47 | sub component ($;%) { |
71d3df94 |
48 | my ($name, %args) = @_; |
85ebb635 |
49 | my $caller = caller; |
71d3df94 |
50 | $args{dependencies} ||= {}; |
51 | $args{dependencies}{application_name} = depends_on( '/application_name' ); |
52 | |
129508fb |
53 | my $lifecycle = $args{lifecycle}; |
54 | my %catalyst_lifecycles = map { $_ => 1 } qw/ COMPONENTSingleton Request /; |
55 | $args{lifecycle} = $lifecycle |
56 | ? $catalyst_lifecycles{$lifecycle} ? "+Catalyst::IOC::LifeCycle::$lifecycle" : $lifecycle |
57 | : 'Singleton' |
58 | ; |
59 | |
71d3df94 |
60 | # FIXME - check $args{type} here! |
61 | |
cdd4485f |
62 | my $component_name = join '::', ( |
85ebb635 |
63 | ${"${caller}::current_container"}->resolve(service => '/application_name'), |
64 | ucfirst(${"${caller}::current_container"}->name), |
cdd4485f |
65 | $name |
66 | ); |
67 | |
7cd05fd2 |
68 | my $service = Catalyst::IOC::ConstructorInjection->new( |
71d3df94 |
69 | %args, |
129508fb |
70 | name => $name, |
cdd4485f |
71 | catalyst_component_name => $component_name, |
7cd05fd2 |
72 | ); |
85ebb635 |
73 | ${"${caller}::current_container"}->add_service($service); |
71d3df94 |
74 | } |
2336ae0b |
75 | |
fb7aaa61 |
76 | 1; |
51f62e09 |
77 | |
78 | __END__ |
79 | |
80 | =pod |
81 | |
82 | =head1 NAME |
83 | |
84 | Catalyst::IOC - IOC for Catalyst, based on Bread::Board |
85 | |
86 | =head1 SYNOPSIS |
87 | |
4e4e003e |
88 | package MyApp::Container; |
9226f304 |
89 | use Moose; |
4e4e003e |
90 | use Catalyst::IOC; |
9226f304 |
91 | extends 'Catalyst::IOC::Container'; |
92 | |
93 | container { |
94 | model { |
95 | # default component |
96 | component Foo => (); |
97 | |
98 | # model Bar needs model Foo to be built before |
99 | # and Bar's constructor gets Foo as a parameter |
100 | component Bar => ( dependencies => [ |
101 | depends_on('/model/Foo'), |
102 | ]); |
103 | |
104 | # Baz is rebuilt once per HTTP request |
105 | component Baz => ( lifecycle => 'Request' ); |
106 | |
107 | # built only once per application life time |
108 | component Quux => ( lifecycle => 'Singleton' ); |
109 | |
110 | # built once per app life time and uses an external model, |
111 | # outside the default directory |
112 | # no need for wrappers or Catalyst::Model::Adaptor |
113 | component Fnar => ( |
114 | lifecycle => 'Singleton', |
115 | class => 'My::External::Class', |
116 | ); |
117 | }; |
118 | view { |
119 | component HTML => (); |
120 | }; |
121 | controller { |
122 | component Root => (); |
123 | }; |
4e4e003e |
124 | } |
125 | |
51f62e09 |
126 | =head1 DESCRIPTION |
127 | |
9226f304 |
128 | Catalyst::IOC provides "sugar" methods to extend the behavior of the default |
129 | Catalyst container. |
130 | |
51f62e09 |
131 | =head1 METHODS |
132 | |
4bb29053 |
133 | =head2 container |
134 | |
9226f304 |
135 | Sets up the root container to be customised. |
136 | |
4bb29053 |
137 | =head2 model |
138 | |
9226f304 |
139 | Sets up the model container to be customised. |
140 | |
4bb29053 |
141 | =head2 view |
142 | |
9226f304 |
143 | Sets up the view container to be customised. |
144 | |
4bb29053 |
145 | =head2 controller |
146 | |
9226f304 |
147 | Sets up the controller container to be customised. |
148 | |
4bb29053 |
149 | =head2 component |
150 | |
9226f304 |
151 | Adds a component to the subcontainer. Works like L<Bread::Board::service>. |
152 | |
51f62e09 |
153 | =head1 AUTHORS |
154 | |
155 | Catalyst Contributors, see Catalyst.pm |
156 | |
4e4e003e |
157 | =head1 SEE ALSO |
158 | |
159 | L<Bread::Board> |
160 | |
51f62e09 |
161 | =head1 COPYRIGHT |
162 | |
163 | This library is free software. You can redistribute it and/or modify it under |
164 | the same terms as Perl itself. |
165 | |
166 | =cut |