Add built local::lib
[catagits/Gitalist.git] / local-lib5 / lib / perl5 / Moose / Cookbook / Basics / Recipe10.pod
1
2 =pod
3
4 =head1 NAME
5
6 Moose::Cookbook::Basics::Recipe10 - Using BUILDARGS and BUILD to hook into object construction
7
8 =head1 SYNOPSIS
9
10   package Person;
11
12   has 'ssn' => (
13       is        => 'ro',
14       isa       => 'Str',
15       predicate => 'has_ssn',
16   );
17
18   has 'country_of_residence' => (
19       is      => 'ro',
20       isa     => 'Str',
21       default => 'usa'
22   );
23
24   has 'first_name' => (
25       is  => 'ro',
26       isa => 'Str',
27   );
28
29   has 'last_name' => (
30       is  => 'ro',
31       isa => 'Str',
32   );
33
34   around BUILDARGS => sub {
35       my $orig = shift;
36       my $class = shift;
37
38       if ( @_ == 1 && ! ref $_[0] ) {
39           return $class->$orig(ssn => $_[0]);
40       }
41       else {
42           return $class->$orig(@_);
43       }
44   };
45
46   sub BUILD {
47       my $self = shift;
48
49       if ( $self->country_of_residence eq 'usa' ) {
50           die 'Cannot create a Person who lives in the USA without an ssn.'
51               unless $self->has_ssn;
52       }
53   }
54
55 =head1 DESCRIPTION
56
57 This recipe demonstrates the use of C<BUILDARGS> and C<BUILD>. By
58 defining these methods, we can hook into the object construction
59 process without overriding C<new>.
60
61 The C<BUILDARGS> method is called I<before> an object has been
62 created. It is called as a class method, and receives all of the
63 parameters passed to the C<new> method. It is expected to do something
64 with these arguments and return a hash reference. The keys of the hash
65 must be attribute C<init_arg>s.
66
67 The primary purpose of C<BUILDARGS> is to allow a class to accept
68 something other than named arguments. In the case of our C<Person>
69 class, we are allowing it to be called with a single argument, a
70 social security number:
71
72   my $person = Person->new('123-45-6789');
73
74 The key part of our C<BUILDARGS> is this conditional:
75
76       if ( @_ == 1 && ! ref $_[0] ) {
77           return $class->$orig(ssn => $_[0]);
78       }
79
80 By default, Moose constructors accept a list of key-value pairs, or a
81 hash reference. We need to make sure that C<$_[0]> is not a reference
82 before assuming it is a social security number.
83
84 We call the original C<BUILDARGS> method to handle all the other
85 cases. You should always do this in your own C<BUILDARGS> methods,
86 since L<Moose::Object> provides its own C<BUILDARGS> method that
87 handles hash references and a list of key-value pairs.
88
89 The C<BUILD> method is called I<after> the object is constructed, but
90 before it is returned to the caller. The C<BUILD> method provides an
91 opportunity to check the object state as a whole. This is a good place
92 to put logic that cannot be expressed as a type constraint on a single
93 attribute.
94
95 In the C<Person> class, we need to check the relationship between two
96 attributes, C<ssn> and C<country_of_residence>. We throw an exception
97 if the object is not logically consistent.
98
99 =head1 MORE CONSIDERATIONS
100
101 This recipe is made significantly simpler because all of the
102 attributes are read-only. If the C<country_of_residence> attribute
103 were settable, we would need to check that a Person had an C<ssn> if
104 the new country was C<usa>. This could be done with a C<before>
105 modifier.
106
107 =head1 CONCLUSION
108
109 We have repeatedly discouraged overriding C<new> in Moose
110 classes. This recipe shows how you can use C<BUILDARGS> and C<BUILD>
111 to hook into object construction without overriding C<new>
112
113 The C<BUILDARGS> method lets us expand on Moose's built-in parameter
114 handling for constructors. The C<BUILD> method lets us implement
115 logical constraints across the whole object after it is created.
116
117 =head1 AUTHOR
118
119 Dave Rolsky E<lt>autarch@urth.orgE<gt>
120
121 =head1 COPYRIGHT AND LICENSE
122
123 Copyright 2006-2009 by Infinity Interactive, Inc.
124
125 L<http://www.iinteractive.com>
126
127 This library is free software; you can redistribute it and/or modify
128 it under the same terms as Perl itself.
129
130 =cut