6487561622c6a96b7e2dca294fa09b4a197de2b6
[gitmo/Moose.git] / t / 030_roles / 013_method_aliasing_in_composition.t
1 #!/usr/bin/perl
2
3 use strict;
4 use warnings;
5
6 use Test::More;
7 use Test::Exception;
8
9
10 {
11     package My::Role;
12     use Moose::Role;
13
14     sub foo { 'Foo::foo' }
15     sub bar { 'Foo::bar' }
16     sub baz { 'Foo::baz' }
17
18     requires 'role_bar';
19
20     package My::Class;
21     use Moose;
22
23     ::lives_ok {
24         with 'My::Role' => { -alias => { bar => 'role_bar' } };
25     } '... this succeeds';
26
27     package My::Class::Failure;
28     use Moose;
29
30     ::throws_ok {
31         with 'My::Role' => { -alias => { bar => 'role_bar' } };
32     } qr/Cannot create a method alias if a local method of the same name exists/, '... this succeeds';
33
34     sub role_bar { 'FAIL' }
35 }
36
37 ok(My::Class->meta->has_method($_), "we have a $_ method") for qw(foo baz bar role_bar);
38
39 {
40     package My::OtherRole;
41     use Moose::Role;
42
43     ::lives_ok {
44         with 'My::Role' => { -alias => { bar => 'role_bar' } };
45     } '... this succeeds';
46
47     sub bar { 'My::OtherRole::bar' }
48
49     package My::OtherRole::Failure;
50     use Moose::Role;
51
52     ::throws_ok {
53         with 'My::Role' => { -alias => { bar => 'role_bar' } };
54     } qr/Cannot create a method alias if a local method of the same name exists/, '... cannot alias to a name that exists';
55
56     sub role_bar { 'FAIL' }
57 }
58
59 ok(My::OtherRole->meta->has_method($_), "we have a $_ method") for qw(foo baz role_bar);
60 ok(My::OtherRole->meta->requires_method('bar'), '... and the &bar method is required');
61 ok(!My::OtherRole->meta->requires_method('role_bar'), '... and the &role_bar method is not required');
62
63 {
64     package My::AliasingRole;
65     use Moose::Role;
66
67     ::lives_ok {
68         with 'My::Role' => { -alias => { bar => 'role_bar' } };
69     } '... this succeeds';
70 }
71
72 ok(My::AliasingRole->meta->has_method($_), "we have a $_ method") for qw(foo baz role_bar);
73 ok(!My::AliasingRole->meta->requires_method('bar'), '... and the &bar method is not required');
74
75 {
76     package Foo::Role;
77     use Moose::Role;
78
79     sub foo { 'Foo::Role::foo' }
80
81     package Bar::Role;
82     use Moose::Role;
83
84     sub foo { 'Bar::Role::foo' }
85
86     package Baz::Role;
87     use Moose::Role;
88
89     sub foo { 'Baz::Role::foo' }
90
91     package My::Foo::Class;
92     use Moose;
93
94     ::lives_ok {
95         with 'Foo::Role' => { -alias => { 'foo' => 'foo_foo' }, -excludes => 'foo' },
96              'Bar::Role' => { -alias => { 'foo' => 'bar_foo' }, -excludes => 'foo' },
97              'Baz::Role';
98     } '... composed our roles correctly';
99
100     package My::Foo::Class::Broken;
101     use Moose;
102
103     ::throws_ok {
104         with 'Foo::Role' => { -alias => { 'foo' => 'foo_foo' }, -excludes => 'foo' },
105              'Bar::Role' => { -alias => { 'foo' => 'foo_foo' }, -excludes => 'foo' },
106              'Baz::Role';
107     } qr/Due to a method name conflict in roles 'Bar::Role' and 'Foo::Role', the method 'foo_foo' must be implemented or excluded by 'My::Foo::Class::Broken'/,
108       '... composed our roles correctly';
109 }
110
111 {
112     my $foo = My::Foo::Class->new;
113     isa_ok($foo, 'My::Foo::Class');
114     can_ok($foo, $_) for qw/foo foo_foo bar_foo/;
115     is($foo->foo, 'Baz::Role::foo', '... got the right method');
116     is($foo->foo_foo, 'Foo::Role::foo', '... got the right method');
117     is($foo->bar_foo, 'Bar::Role::foo', '... got the right method');
118 }
119
120 {
121     package My::Foo::Role;
122     use Moose::Role;
123
124     ::lives_ok {
125         with 'Foo::Role' => { -alias => { 'foo' => 'foo_foo' }, -excludes => 'foo' },
126              'Bar::Role' => { -alias => { 'foo' => 'bar_foo' }, -excludes => 'foo' },
127              'Baz::Role';
128     } '... composed our roles correctly';
129 }
130
131 ok(My::Foo::Role->meta->has_method($_), "we have a $_ method") for qw/foo foo_foo bar_foo/;;
132 ok(!My::Foo::Role->meta->requires_method('foo'), '... and the &foo method is not required');
133
134
135 {
136     package My::Foo::Role::Other;
137     use Moose::Role;
138
139     ::lives_ok {
140         with 'Foo::Role' => { -alias => { 'foo' => 'foo_foo' }, -excludes => 'foo' },
141              'Bar::Role' => { -alias => { 'foo' => 'foo_foo' }, -excludes => 'foo' },
142              'Baz::Role';
143     } '... composed our roles correctly';
144 }
145
146 ok(!My::Foo::Role::Other->meta->has_method('foo_foo'), "we dont have a foo_foo method");
147 ok(My::Foo::Role::Other->meta->requires_method('foo_foo'), '... and the &foo method is required');
148
149 {
150     package My::Foo::AliasOnly;
151     use Moose;
152
153     ::lives_ok {
154         with 'Foo::Role' => { -alias => { 'foo' => 'foo_foo' } },
155     } '... composed our roles correctly';
156 }
157
158 ok(My::Foo::AliasOnly->meta->has_method('foo'), 'we have a foo method');
159 ok(My::Foo::AliasOnly->meta->has_method('foo_foo'), '.. and the aliased foo_foo method');
160
161 {
162     package Role::Foo;
163     use Moose::Role;
164
165     sub x1 {}
166     sub y1 {}
167 }
168
169 {
170     package Role::Bar;
171     use Moose::Role;
172
173     use Test::Exception;
174
175     lives_ok {
176         with 'Role::Foo' => {
177             -alias    => { x1 => 'foo_x1' },
178             -excludes => ['y1'],
179         };
180     }
181     'Compose Role::Foo into Role::Bar with alias and exclude';
182
183     sub x1 {}
184     sub y1 {}
185 }
186
187 {
188     my $bar = Role::Bar->meta;
189     ok( $bar->has_method($_), "has $_ method" )
190         for qw( x1 y1 foo_x1 );
191 }
192
193 {
194     package Role::Baz;
195     use Moose::Role;
196
197     use Test::Exception;
198
199     lives_ok {
200         with 'Role::Foo' => {
201             -alias    => { x1 => 'foo_x1' },
202             -excludes => ['y1'],
203         };
204     }
205     'Compose Role::Foo into Role::Baz with alias and exclude';
206 }
207
208 {
209     my $baz = Role::Baz->meta;
210     ok( $baz->has_method($_), "has $_ method" )
211         for qw( x1 foo_x1 );
212     ok( ! $baz->has_method('y1'), 'Role::Baz has no y1 method' );
213 }
214
215 done_testing;