Provided by: libmoox-buildargs-perl_0.08-2_all bug

NAME

       MooX::BuildArgsHooks - Structured BUILDARGS.

SYNOPSIS

           package Foo;
           use Moo;
           with 'MooX::BuildArgsHooks';

           has bar => (is=>'ro');

           around NORMALIZE_BUILDARGS => sub{
               my ($orig, $class, @args) = @_;
               @args = $class->$orig( @args );
               return( bar=>$args[0] ) if @args==1 and ref($args[0]) ne 'HASH';
               return @args;
           };

           around TRANSFORM_BUILDARGS => sub{
               my ($orig, $class, $args) = @_;
               $args = $class->$orig( $args );
               $args->{bar} = ($args->{bar}||0) + 10;
               return $args;
           };

           around FINALIZE_BUILDARGS => sub{
               my ($orig, $class, $args) = @_;
               $args = $class->$orig( $args );
               $args->{bar}++;
               return $args;
           };

           print Foo->new( 3 )->bar(); # 14

DESCRIPTION

       This module installs some hooks directly into Moo which allow for more fine-grained access
       to the phases of "BUILDARGS".  The reason this is important is because if you have various
       roles and classes modifying BUILDARGS you will often end up with weird behaviors depending
       on what order the various BUILDARGS wrappers are applied in.  By breaking up argument
       processing into three steps (normalize, transform, and finalize) these conflicts are much
       less likely to arise.

       To further avoid these kinds of issues, and this applies to any system where you would
       "around" methods from a consuming role or super class not just BUILDARGS, it is
       recommended that you implement your extensions via methods.  This way if something
       inherits from your role or class they can treat your method as a hook.  For example:

           around TRANSFORM_BUILDARGS => sub{
               my ($class, $orig, $args) = @_;
               $args = $class->$orig( $args );
               return $class->TRANSFORM_FOO_BUILDARGS( $args );
           };

           sub TRANSFORM_FOO_BUILDARGS {
               my ($class, $args) = @_;
               $args->{bar} = ($args->{bar}||0) + 10;
               return $args;
           }

       Then if some other code wishes to inject code before or after the "Foo" class transforming
       BUILDARGS they can do so at very specific points.

HOOKS

       A hook in the context of this module is just a method that has been declared in the
       inheritance hierarchy and is made available for consuming roles and classes to apply
       method modifiers to.

   NORMALIZE_BUILDARGS
           around NORMALIZE_BUILDARGS => sub{
               my ($orig, $class, @args) = @_;

               # Make sure you let other normalizations happen.
               @args = $class->$orig( @args );

               # Do your normalization logic.
               ...

               return @args;
           };

       Used to do some basic normalization of arguments from some custom format to a format
       acceptable to Moo (a hash or a hashref).

       This is useful, for example, when you want to support single arguments.  For example:

           around NORMALIZE_BUILDARGS => sub{
               my ($orig, $class, @args) = @_;

               # If only one argument is passed in assume that it is
               # the value for the foo attribute.
               if (@args==1 and ref($args[0]) ne 'HASH') {
                   @args = { foo => $args[0] };
               }

               @args = $class->$orig( @args );

               return @args;
           };

       Or you could just use MooX::SingleArg.

   TRANSFORM_BUILDARGS
           around TRANSFORM_BUILDARGS => sub{
               my ($orig, $class, $args) = @_;

               # Make sure you let any other transformations happen.
               $args = $class->$orig( $args );

               # Do your transformations.
               ...

               return $args;
           };

       This hook is the workhorse where much of the "BUILDARGS" work typically happens.  By the
       time this hook is called the arguments will always be in hashref form, not a list, and a
       hashref must be returned.

   FINALIZE_BUILDARGS
           around FINAL_BUILDARGS => sub{
               my ($orig, $class, $args) = @_;

               # Let any other hooks have a turn.
               $args = $class->$orig( $args );

               # Do your finalization logic.
               ...

               return $args;
           };

       This hook works just like "TRANSFORM_BUILDARGS" except that it happens after it and is
       meant to be used by hooks that are the last step in the argument building process and need
       access to the arguments after most all other steps have completed.

SEE ALSO

       •   MooX::BuildArgs

       •   MooX::MethodProxyArgs

       •   MooX::Rebuild

       •   MooX::SingleArg

SUPPORT

       See "SUPPORT" in MooX::BuildArgs.

AUTHORS

       See "AUTHORS" in MooX::BuildArgs.

LICENSE

       See "LICENSE" in MooX::BuildArgs.