From: Matt S Trout Date: Thu, 19 Apr 2012 21:11:54 +0000 (+0000) Subject: change role-to-role application to allow method shadowing X-Git-Tag: 2.0800~45 X-Git-Url: http://git.shadowcat.co.uk/gitweb/gitweb.cgi?a=commitdiff_plain;h=2afe5289a42e908d111db381a826c66d93fbb913;p=gitmo%2FMoose.git change role-to-role application to allow method shadowing --- diff --git a/lib/Moose/Meta/Role/Application/ToRole.pm b/lib/Moose/Meta/Role/Application/ToRole.pm index e8ab886..97ce038 100644 --- a/lib/Moose/Meta/Role/Application/ToRole.pm +++ b/lib/Moose/Meta/Role/Application/ToRole.pm @@ -85,12 +85,9 @@ sub apply_methods { if ( $role2_method && $role2_method->body != $method->body ) { - # method conflicts between roles result in the method becoming - # a requirement - $role2->add_conflicting_method( - name => $method_name, - roles => [ $role1->name, $role2->name ], - ); + # method conflicts between roles used to result in the method + # becoming a requirement but now are permitted just like + # for classes, hence no code in this branch anymore. } else { $role2->add_method( diff --git a/t/roles/method_aliasing_in_composition.t b/t/roles/method_aliasing_in_composition.t index c6146a7..c392eae 100644 --- a/t/roles/method_aliasing_in_composition.t +++ b/t/roles/method_aliasing_in_composition.t @@ -57,7 +57,7 @@ ok(My::Class->meta->has_method($_), "we have a $_ method") for qw(foo baz bar ro } ok(My::OtherRole->meta->has_method($_), "we have a $_ method") for qw(foo baz role_bar); -ok(My::OtherRole->meta->requires_method('bar'), '... and the &bar method is required'); +ok(!My::OtherRole->meta->requires_method('bar'), '... and the &bar method is not required'); ok(!My::OtherRole->meta->requires_method('role_bar'), '... and the &role_bar method is not required'); { diff --git a/t/roles/method_exclusion_in_composition.t b/t/roles/method_exclusion_in_composition.t index 64c3605..656b437 100644 --- a/t/roles/method_exclusion_in_composition.t +++ b/t/roles/method_exclusion_in_composition.t @@ -37,7 +37,7 @@ ok(!My::Class->meta->has_method('bar'), '... but we excluded bar'); ok(My::OtherRole->meta->has_method($_), "we have a $_ method") for qw(foo bar baz); ok(!My::OtherRole->meta->requires_method('foo'), '... and the &foo method is not required'); -ok(My::OtherRole->meta->requires_method('bar'), '... and the &bar method is required'); +ok(!My::OtherRole->meta->requires_method('bar'), '... and the &bar method is not required'); { package Foo::Role; diff --git a/t/roles/more_alias_and_exclude.t b/t/roles/more_alias_and_exclude.t index 62d3098..41fd795 100644 --- a/t/roles/more_alias_and_exclude.t +++ b/t/roles/more_alias_and_exclude.t @@ -65,4 +65,26 @@ is($c->foo_gorch, 'Foo::gorch', '... got the right method'); is($c->baz_foo, 'Baz::foo', '... got the right method'); is($c->baz_bar, 'Baz::bar', '... got the right method'); +{ + package Splunk; + + use Moose::Role; + + sub baz { 'Splunk::baz' } + sub gorch { 'Splunk::gorch' } + + ::is(::exception { with 'Foo' }, undef, 'role to role application works'); + + package My::Class2; + + use Moose; + + ::is(::exception { with 'Splunk' }, undef, 'and the role can be consumed'); +} + +is(My::Class2->foo, 'Foo::foo', '... got the right method'); +is(My::Class2->bar, 'Foo::bar', '... got the right method'); +is(My::Class2->baz, 'Splunk::baz', '... got the right method'); +is(My::Class2->gorch, 'Splunk::gorch', '... got the right method'); + done_testing; diff --git a/t/roles/overriding.t b/t/roles/overriding.t index 6f7d11b..cc4027d 100644 --- a/t/roles/overriding.t +++ b/t/roles/overriding.t @@ -48,38 +48,26 @@ is( Class::A->new->xxy, "Role::B::xxy", "... got the right xxy method" ); { # check that when a role is added to another role - # and they conflict and the method they conflict - # with is then required. + # that the consumer's method shadows just like for classes. - package Role::A::Conflict; + package Role::A::Shadow; use Moose::Role; with 'Role::A'; - sub bar { 'Role::A::Conflict::bar' } + sub bar { 'Role::A::Shadow::bar' } - package Class::A::Conflict; - use Moose; - - ::like( ::exception { - with 'Role::A::Conflict'; - }, qr/Due to a method name conflict in roles 'Role::A' and 'Role::A::Conflict', the method 'bar' must be implemented or excluded by 'Class::A::Conflict'/, '... did not fufill the requirement of &bar method' ); - - package Class::A::Resolved; + package Class::A::Shadow; use Moose; ::is( ::exception { - with 'Role::A::Conflict'; + with 'Role::A::Shadow'; }, undef, '... did fufill the requirement of &bar method' ); - - sub bar { 'Class::A::Resolved::bar' } } -ok(Role::A::Conflict->meta->requires_method('bar'), '... Role::A::Conflict created the bar requirement'); - -can_ok( Class::A::Resolved->new, qw(bar) ); +can_ok( Class::A::Shadow->new, qw(bar) ); -is( Class::A::Resolved->new->bar, 'Class::A::Resolved::bar', "... got the right bar method" ); +is( Class::A::Shadow->new->bar, 'Role::A::Shadow::bar', "... got the right bar method" ); { # check that when two roles are composed, they conflict @@ -131,24 +119,23 @@ ok(!Role::F->meta->requires_method('foo'), '... Role::F fufilled the &foo requir # by a role, but also new ones can be # created just as easily ... - package Role::D::And::E::Conflict; + package Role::D::And::E::NoConflict; use Moose::Role; ::is( ::exception { with qw(Role::D Role::E); # conflict between 'foo's here - }, undef, "... define role Role::D::And::E::Conflict" ); + }, undef, "... define role Role::D::And::E::NoConflict" ); - sub foo { 'Role::D::And::E::Conflict::foo' } # this overrides ... + sub foo { 'Role::D::And::E::NoConflict::foo' } # this overrides ... - # but these conflict - sub xxy { 'Role::D::And::E::Conflict::xxy' } - sub bar { 'Role::D::And::E::Conflict::bar' } + sub xxy { 'Role::D::And::E::NoConflict::xxy' } # and so do these ... + sub bar { 'Role::D::And::E::NoConflict::bar' } } -ok(!Role::D::And::E::Conflict->meta->requires_method('foo'), '... Role::D::And::E::Conflict fufilled the &foo requirement'); -ok(Role::D::And::E::Conflict->meta->requires_method('xxy'), '... Role::D::And::E::Conflict adds the &xxy requirement'); -ok(Role::D::And::E::Conflict->meta->requires_method('bar'), '... Role::D::And::E::Conflict adds the &bar requirement'); +ok(!Role::D::And::E::NoConflict->meta->requires_method('foo'), '... Role::D::And::E::NoConflict fufilled the &foo requirement'); +ok(!Role::D::And::E::NoConflict->meta->requires_method('xxy'), '... Role::D::And::E::NoConflict fulfilled the &xxy requirement'); +ok(!Role::D::And::E::NoConflict->meta->requires_method('bar'), '... Role::D::And::E::NoConflict fulfilled the &bar requirement'); { # conflict propagation