Turn composition_class_roles into a plain method.
[gitmo/Moose.git] / t / 050_metaclasses / 030_metarole_combination.t
CommitLineData
87f55e33 1use strict;
2use warnings;
3use Test::More;
4
5our @applications;
6
7{
67dac033 8 package CustomApplication;
9 use Moose::Role;
10
11 after apply_methods => sub {
12 my ( $self, $role, $other ) = @_;
13 $self->apply_custom( $role, $other );
87f55e33 14 };
15
16 sub apply_custom {
17 shift;
18 push @applications, [@_];
67dac033 19 }
87f55e33 20}
21
22{
23 package CustomApplication::ToClass;
24 use Moose::Role;
67dac033 25
87f55e33 26 with 'CustomApplication';
27}
28
29{
30 package CustomApplication::ToRole;
31 use Moose::Role;
67dac033 32
87f55e33 33 with 'CustomApplication';
34}
35
36{
37 package CustomApplication::ToInstance;
38 use Moose::Role;
67dac033 39
87f55e33 40 with 'CustomApplication';
41}
42
43{
44 package CustomApplication::Composite;
45 use Moose::Role;
67dac033 46
87f55e33 47 with 'CustomApplication';
67dac033 48
87f55e33 49 around apply_custom => sub {
67dac033 50 my ( $next, $self, $composite, $other ) = @_;
51 for my $role ( @{ $composite->get_roles } ) {
52 $self->$next( $role, $other );
87f55e33 53 }
54 };
55}
56
57{
58 package CustomApplication::Composite::ToClass;
59 use Moose::Role;
67dac033 60
87f55e33 61 with 'CustomApplication::Composite';
62}
63
64{
65 package CustomApplication::Composite::ToRole;
66 use Moose::Role;
67dac033 67
87f55e33 68 with 'CustomApplication::Composite';
69}
70
71{
72 package CustomApplication::Composite::ToInstance;
73 use Moose::Role;
67dac033 74
87f55e33 75 with 'CustomApplication::Composite';
76}
77
78{
79 package Role::Composite;
80 use Moose::Role;
67dac033 81
87f55e33 82 around apply_params => sub {
67dac033 83 my ( $next, $self, @args ) = @_;
87f55e33 84 return Moose::Util::MetaRole::apply_metaclass_roles(
67dac033 85 for_class => $self->$next(@args),
86 application_to_class_class_roles =>
87 ['CustomApplication::Composite::ToClass'],
88 application_to_role_class_roles =>
89 ['CustomApplication::Composite::ToRole'],
90 application_to_instance_class_roles =>
91 ['CustomApplication::Composite::ToInstance'],
87f55e33 92 );
93 };
94}
95
96{
97 package Role::WithCustomApplication;
98 use Moose::Role;
67dac033 99
4701ceff 100 around composition_class_roles => sub {
101 my ($orig, $self) = @_;
102 return $self->$orig, 'Role::Composite';
103 };
87f55e33 104}
105
106{
107 package CustomRole;
108 Moose::Exporter->setup_import_methods(
109 also => 'Moose::Role',
110 );
111
112 sub init_meta {
67dac033 113 my ( $self, %options ) = @_;
87f55e33 114 return Moose::Util::MetaRole::apply_metaclass_roles(
67dac033 115 for_class => Moose::Role->init_meta(%options),
116 metaclass_roles => ['Role::WithCustomApplication'],
117 application_to_class_class_roles =>
118 ['CustomApplication::ToClass'],
119 application_to_role_class_roles => ['CustomApplication::ToRole'],
120 application_to_instance_class_roles =>
121 ['CustomApplication::ToInstance'],
87f55e33 122 );
123 }
124}
125
126{
127 package My::Role::Normal;
128 use Moose::Role;
129}
130
131{
132 package My::Role::Special;
133 CustomRole->import;
134}
135
67dac033 136ok( My::Role::Normal->meta->isa('Moose::Meta::Role'), "sanity check" );
137ok( My::Role::Special->meta->isa('Moose::Meta::Role'),
138 "using custom application roles does not change the role metaobject's class"
139);
140ok( My::Role::Special->meta->meta->does_role('Role::WithCustomApplication'),
141 "the role's metaobject has custom applications" );
4701ceff 142is_deeply( [My::Role::Special->meta->composition_class_roles],
67dac033 143 ['Role::Composite'],
144 "the role knows about the specified composition class" );
87f55e33 145
146{
147 package Foo;
148 use Moose;
67dac033 149
87f55e33 150 local @applications;
151 with 'My::Role::Special';
67dac033 152
153 ::is( @applications, 1, 'one role application' );
154 ::is( $applications[0]->[0]->name, 'My::Role::Special',
155 "the application's first role was My::Role::Special'" );
156 ::is( $applications[0]->[1]->name, 'Foo',
157 "the application provided an additional role" );
87f55e33 158}
159
160{
161 package Bar;
162 use Moose::Role;
67dac033 163
87f55e33 164 local @applications;
165 with 'My::Role::Special';
67dac033 166
167 ::is( @applications, 1 );
168 ::is( $applications[0]->[0]->name, 'My::Role::Special' );
169 ::is( $applications[0]->[1]->name, 'Bar' );
87f55e33 170}
171
172{
173 package Baz;
174 use Moose;
67dac033 175
87f55e33 176 my $i = Baz->new;
177 local @applications;
178 My::Role::Special->meta->apply($i);
67dac033 179
180 ::is( @applications, 1 );
181 ::is( $applications[0]->[0]->name, 'My::Role::Special' );
182 ::ok( $applications[0]->[1]->is_anon_class );
183 ::ok( $applications[0]->[1]->name->isa('Baz') );
87f55e33 184}
185
186{
187 package Corge;
188 use Moose;
67dac033 189
87f55e33 190 local @applications;
191 with 'My::Role::Normal', 'My::Role::Special';
67dac033 192
193 ::is( @applications, 2 );
194 ::is( $applications[0]->[0]->name, 'My::Role::Normal' );
195 ::is( $applications[0]->[1]->name, 'Corge' );
196 ::is( $applications[1]->[0]->name, 'My::Role::Special' );
197 ::is( $applications[1]->[1]->name, 'Corge' );
87f55e33 198}
199
200{
201 package Thud;
202 use Moose::Role;
67dac033 203
87f55e33 204 local @applications;
205 with 'My::Role::Normal', 'My::Role::Special';
67dac033 206
207 ::is( @applications, 2 );
208 ::is( $applications[0]->[0]->name, 'My::Role::Normal' );
209 ::is( $applications[0]->[1]->name, 'Thud' );
210 ::is( $applications[1]->[0]->name, 'My::Role::Special' );
211 ::is( $applications[1]->[1]->name, 'Thud' );
87f55e33 212}
213
214{
215 package Garply;
216 use Moose;
67dac033 217
87f55e33 218 my $i = Garply->new;
219 local @applications;
220 Moose::Meta::Role->combine(
67dac033 221 [ 'My::Role::Normal' => undef ],
222 [ 'My::Role::Special' => undef ],
87f55e33 223 )->apply($i);
67dac033 224
225 ::is( @applications, 2 );
226 ::is( $applications[0]->[0]->name, 'My::Role::Normal' );
227 ::ok( $applications[0]->[1]->is_anon_class );
228 ::ok( $applications[0]->[1]->name->isa('Garply') );
229 ::is( $applications[1]->[0]->name, 'My::Role::Special' );
230 ::ok( $applications[1]->[1]->is_anon_class );
231 ::ok( $applications[1]->[1]->name->isa('Garply') );
87f55e33 232}
233
234done_testing;