Role::Basic::Philosophy man page on Alpinelinux

Man page or keyword search:  
man Server   18016 pages
apropos Keyword Search (all sections)
Output format
Alpinelinux logo
[printable version]

Role::Basic::PhilosophUser Contributed Perl DocumentRole::Basic::Philosophy(3)

NAME
       Role::Basic::Philosophy - Why Role::Basic exists.

RATIONALE
       Note: the words "trait" and "role" will be used interchangeably
       throughout this documentation.

       After years of using roles, your author has found that many people
       would be happy to use roles but are not willing/comfortable with using
       Moose.  This module implements roles and nothing else. It does so in a
       (relatively) simple bit of code.	 However, you should be aware that
       there are some differences between Role::Basic and Moose::Role.

       Moose is a fantastic technology and your author is quite happy with it.
       He urges you to check it out and perhaps even consider Role::Basic a
       "stepping-stone" to Moose.  However, after an informal poll with many
       respondents replying on blogs.perl.org, Twitter, Facebook and private
       email unanimously saying they wanted this module for roles and not as a
       stepping-stone to Moose, your author took the liberty of deciding to
       implement traits in a rather faithful fashion, rather than strictly
       adhere to the design of Moose::Role.  For areas where we differ,
       Role::Basic intends to be more restrictive when syntax is the same.
       This allows an easier migration to Moose::Role when the time is right.
       Otherwise, Role::Basic will offer a different syntax to avoid
       confusion.

TRAITS
       As most of you probably know, roles are the Perl implmentation of
       traits as described in <http://scg.unibe.ch/research/traits/>.  (The
       name "role" was chosen because "trait" was already used in Perl 6.)  In
       particular, we direct you to two papers, both of which are easy to
       read:

       ·   <http://scg.unibe.ch/scgbib?_s=tgXJjGrs0380ejY6&_k=Swgdwx_C&query=nathanael+traits+composable+units+ecoop&display=abstract&_n&19>

	   The seminal "traits paper" which much of the documentation refers
	   to.

       ·   <http://scg.unibe.ch/scgbib?_s=tgXJjGrs0380ejY6&_k=Swgdwx_C&query=traits+the+formal+model&display=abstract&_n&23>

	   "Traits: The Formal Model".

	   While less well-known, this relatively easy to read paper outlines
	   the mathematical underpinnings of traits and explains several
	   design decisions taken here.

       It is important to refer back to those papers because Role::Basic
       attempts to implements traits as described in the research, whereas
       Moose::Role attempts to implement something very similar to traits, but
       with more of a "Perlish" feel.  This is not intended as a criticism of
       Moose::Role, but merely an attempt to alert the reader to key
       differences.

   The Basics
       Roles are simply bundles of behavior which classes may use. If you have
       two completely unrelated classes, your code may still require each of
       them to serialize themselves as JSON even though neither class
       naturally has anything to do with JSON (for example, "Person" and
       "Order" classes).  There are a number of approaches to this problem but
       if you're here I'll skip the explanation and assume that you already
       understand roles and would like to know why we don't follow the
       Moose::Role specification.

       As you already probably know, roles allow you to state that your class
       "DOES" some behaviour, and allows you to exclude or alias bits and
       pieces of the roles you're including.  The original specification of
       traits made it clear that this was to be done in such a fashion that no
       matter how you grouped the traits or in which order you used them, the
       outcome behavior would be the same. That's why we have subtle but
       forward-compatible differences with Moose::Role.

       Commutative

       The formal model
       (<http://scg.unibe.ch/archive/papers/Scha02cTraitsModel.pdf>) states
       that trait composition must be commutative (section 3.4, proposition
       1).  This means that:

	   (A + B) = (B + A)

       In other words, it should not matter what order you compose the traits
       in. It is well known that with both inheritance and mixins, this does
       not hold (making refactoring a dicey proposition at times), but when
       method modifiers are used with Moose::Role, the same issues arises
       (from
       <http://blogs.perl.org/users/ovid/2010/12/rolebasic---when-you-only-want-roles.html>):

	   {
	       package Some::Role;
	       use Moose::Role;
	       requires qw(some_method);

	       before some_method => sub {
		   my $self = shift;
		   $self->some_number( $self->some_number + 2 );
	       };
	   }
	   {
	       package Another::Role;
	       use Moose::Role;
	       requires qw(some_method);

	       before some_method => sub {
		   my $self = shift;
		   $self->some_number( $self->some_number / 2 );
	       };
	   }
	   {
	       package Some::Class;
	       use Moose;
	       my @roles =
		 int( rand(2) )
		 ? qw(Another::Role Some::Role)
		 : qw(Some::Role Another::Role);
	       with @roles;

	       has some_number => ( is => 'rw', isa => 'Num' );
	       sub some_method { print shift->some_number, $/ }
	   }
	   my $o = Some::Class->new( { some_number => 7 } );
	   $o->some_method;

       If you run this code, it might print 4.5, but it might print 5.5. As
       with mixins and multiple inheritance, you have no way of knowing the
       exact behaviour which will be exhibited short of running the code. No
       introspection will help. This is not an issue with Role::Basic because
       we do not allow method modifiers.  If you think you need them, please
       consider Moose.

       Associative

       The formal model
       (<http://scg.unibe.ch/archive/papers/Scha02cTraitsModel.pdf>) states
       that trait composition must be associative (section 3.4, proposition
       1).  This means that:

	   (A + B) + C = A + (B + C)

       Moose is associative if and only if you do not have multiple methods
       with the same name.  In Moose, if a role providing method M consumes
       one other role which also provides method M, we have a conflict:

	   package Some::Role;
	   use Moose::Role;
	   sub bar { __PACKAGE__ }

	   package Some::Other::Role;
	   use Moose::Role;
	   with 'Some::Role';
	   sub bar { __PACKAGE__ }

	   package Some::Class;
	   use Moose;
	   with 'Some::Other::Role';

	   package main;
	   my $o = Some::Class->new;
	   print $o->bar;

       However, if the role consumes two or more other roles which provide the
       same method, we don't have a conflict:

	   package Some::Role;
	   use Moose::Role;
	   sub bar { __PACKAGE__ }

	   package Some::Other::Role;
	   use Moose::Role;
	   sub bar { __PACKAGE__ }

	   package Another::Role;
	   use Moose::Role;
	   with qw(Some::Role Some::Other::Role);
	   sub bar { __PACKAGE__ }

	   package Some::Class;
	   use Moose;
	   with 'Another::Role';

	   package main;
	   my $o = Some::Class->new;
	   print $o->bar;

       This is because, in Moose, when you have two or more roles consumed,
       any conflicting methods are excluded and considered to be requirements.

       See "Moose::Role composition edge cases" for more explanation:
       <http://search.cpan.org/~drolsky/Moose-1.21/lib/Moose/Spec/Role.pod#Composition_Edge_Cases>.

       This makes roles easy to use at times, but it means that the following
       three groups of roles are not guaranteed to provide the same behavior:

	RoleA does RoleB, RoleC
	RoleB does RoleA, RoleC
	RoleC does RoleA, RoleB

       Further, you as a developer have no way of knowing that we have had
       methods silently excluded without reading all of the code.

       For Role::Basic there are no edge cases. If "RoleA", "RoleB", and
       "RoleC" all provide method M, you are guaranteed to get a conflict at
       composition time and must specifically address the problem. This
       addresses the associative issue because strictly speaking, a trait is
       merely a bundle of services provided, not its name.  Thus, a trait with
       its "foo" method excluded is not the same as itself without the "foo"
       method excluded.

       Benefits of associative and commutative behaviour

       While we recognize that not everyone will be happy with the decisions
       we have made, we have several benefits here:

       ·   We adhere to the formal definition of traits

       ·   Ordering and grouping of traits does not alter their behavior

       ·   We're forward-compatible with Moose::Role

CONCLUSION
       The primary goal of Role::Basic is to provide traits in a simple and
       safe manner. We are huge fans of Moose and Moose::Role and suggest that
       everyone check them out. The decision of Moose::Role to deviate from
       the "associative" and "commutative" deviations from the original traits
       model is, in our experience, less likely to occur with roles than with
       mixins and inhertance, so please do not take this as an indictment, but
       rather in the spirit of TIMTOWTDI.

perl v5.18.2			  2014-05-13	    Role::Basic::Philosophy(3)
[top]

List of man pages available for Alpinelinux

Copyright (c) for man pages and the logo by the respective OS vendor.

For those who want to learn more, the polarhome community provides shell access and support.

[legal] [privacy] [GNU] [policy] [cookies] [netiquette] [sponsors] [FAQ]
Tweet
Polarhome, production since 1999.
Member of Polarhome portal.
Based on Fawad Halim's script.
....................................................................
Vote for polarhome
Free Shell Accounts :: the biggest list on the net