Add built local::lib
[catagits/Gitalist.git] / local-lib5 / man / man3 / Moose::Cookbook::Basics::Recipe4.3pm
1 .\" Automatically generated by Pod::Man v1.37, Pod::Parser v1.3
2 .\"
3 .\" Standard preamble:
4 .\" ========================================================================
5 .de Sh \" Subsection heading
6 .br
7 .if t .Sp
8 .ne 5
9 .PP
10 \fB\\$1\fR
11 .PP
12 ..
13 .de Sp \" Vertical space (when we can't use .PP)
14 .if t .sp .5v
15 .if n .sp
16 ..
17 .de Vb \" Begin verbatim text
18 .ft CW
19 .nf
20 .ne \\$1
21 ..
22 .de Ve \" End verbatim text
23 .ft R
24 .fi
25 ..
26 .\" Set up some character translations and predefined strings.  \*(-- will
27 .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left
28 .\" double quote, and \*(R" will give a right double quote.  | will give a
29 .\" real vertical bar.  \*(C+ will give a nicer C++.  Capital omega is used to
30 .\" do unbreakable dashes and therefore won't be available.  \*(C` and \*(C'
31 .\" expand to `' in nroff, nothing in troff, for use with C<>.
32 .tr \(*W-|\(bv\*(Tr
33 .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p'
34 .ie n \{\
35 .    ds -- \(*W-
36 .    ds PI pi
37 .    if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch
38 .    if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\"  diablo 12 pitch
39 .    ds L" ""
40 .    ds R" ""
41 .    ds C` ""
42 .    ds C' ""
43 'br\}
44 .el\{\
45 .    ds -- \|\(em\|
46 .    ds PI \(*p
47 .    ds L" ``
48 .    ds R" ''
49 'br\}
50 .\"
51 .\" If the F register is turned on, we'll generate index entries on stderr for
52 .\" titles (.TH), headers (.SH), subsections (.Sh), items (.Ip), and index
53 .\" entries marked with X<> in POD.  Of course, you'll have to process the
54 .\" output yourself in some meaningful fashion.
55 .if \nF \{\
56 .    de IX
57 .    tm Index:\\$1\t\\n%\t"\\$2"
58 ..
59 .    nr % 0
60 .    rr F
61 .\}
62 .\"
63 .\" For nroff, turn off justification.  Always turn off hyphenation; it makes
64 .\" way too many mistakes in technical documents.
65 .hy 0
66 .if n .na
67 .\"
68 .\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2).
69 .\" Fear.  Run.  Save yourself.  No user-serviceable parts.
70 .    \" fudge factors for nroff and troff
71 .if n \{\
72 .    ds #H 0
73 .    ds #V .8m
74 .    ds #F .3m
75 .    ds #[ \f1
76 .    ds #] \fP
77 .\}
78 .if t \{\
79 .    ds #H ((1u-(\\\\n(.fu%2u))*.13m)
80 .    ds #V .6m
81 .    ds #F 0
82 .    ds #[ \&
83 .    ds #] \&
84 .\}
85 .    \" simple accents for nroff and troff
86 .if n \{\
87 .    ds ' \&
88 .    ds ` \&
89 .    ds ^ \&
90 .    ds , \&
91 .    ds ~ ~
92 .    ds /
93 .\}
94 .if t \{\
95 .    ds ' \\k:\h'-(\\n(.wu*8/10-\*(#H)'\'\h"|\\n:u"
96 .    ds ` \\k:\h'-(\\n(.wu*8/10-\*(#H)'\`\h'|\\n:u'
97 .    ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'^\h'|\\n:u'
98 .    ds , \\k:\h'-(\\n(.wu*8/10)',\h'|\\n:u'
99 .    ds ~ \\k:\h'-(\\n(.wu-\*(#H-.1m)'~\h'|\\n:u'
100 .    ds / \\k:\h'-(\\n(.wu*8/10-\*(#H)'\z\(sl\h'|\\n:u'
101 .\}
102 .    \" troff and (daisy-wheel) nroff accents
103 .ds : \\k:\h'-(\\n(.wu*8/10-\*(#H+.1m+\*(#F)'\v'-\*(#V'\z.\h'.2m+\*(#F'.\h'|\\n:u'\v'\*(#V'
104 .ds 8 \h'\*(#H'\(*b\h'-\*(#H'
105 .ds o \\k:\h'-(\\n(.wu+\w'\(de'u-\*(#H)/2u'\v'-.3n'\*(#[\z\(de\v'.3n'\h'|\\n:u'\*(#]
106 .ds d- \h'\*(#H'\(pd\h'-\w'~'u'\v'-.25m'\f2\(hy\fP\v'.25m'\h'-\*(#H'
107 .ds D- D\\k:\h'-\w'D'u'\v'-.11m'\z\(hy\v'.11m'\h'|\\n:u'
108 .ds th \*(#[\v'.3m'\s+1I\s-1\v'-.3m'\h'-(\w'I'u*2/3)'\s-1o\s+1\*(#]
109 .ds Th \*(#[\s+2I\s-2\h'-\w'I'u*3/5'\v'-.3m'o\v'.3m'\*(#]
110 .ds ae a\h'-(\w'a'u*4/10)'e
111 .ds Ae A\h'-(\w'A'u*4/10)'E
112 .    \" corrections for vroff
113 .if v .ds ~ \\k:\h'-(\\n(.wu*9/10-\*(#H)'\s-2\u~\d\s+2\h'|\\n:u'
114 .if v .ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'\v'-.4m'^\v'.4m'\h'|\\n:u'
115 .    \" for low resolution devices (crt and lpr)
116 .if \n(.H>23 .if \n(.V>19 \
117 \{\
118 .    ds : e
119 .    ds 8 ss
120 .    ds o a
121 .    ds d- d\h'-1'\(ga
122 .    ds D- D\h'-1'\(hy
123 .    ds th \o'bp'
124 .    ds Th \o'LP'
125 .    ds ae ae
126 .    ds Ae AE
127 .\}
128 .rm #[ #] #H #V #F C
129 .\" ========================================================================
130 .\"
131 .IX Title "Moose::Cookbook::Basics::Recipe4 3"
132 .TH Moose::Cookbook::Basics::Recipe4 3 "2009-05-05" "perl v5.8.7" "User Contributed Perl Documentation"
133 .SH "NAME"
134 Moose::Cookbook::Basics::Recipe4 \- Subtypes, and modeling a simple \fBCompany\fR class hierarchy
135 .SH "SYNOPSIS"
136 .IX Header "SYNOPSIS"
137 .Vb 3
138 \&  package Address;
139 \&  use Moose;
140 \&  use Moose::Util::TypeConstraints;
141 .Ve
142 .PP
143 .Vb 2
144 \&  use Locale::US;
145 \&  use Regexp::Common 'zip';
146 .Ve
147 .PP
148 .Vb 7
149 \&  my $STATES = Locale::US\->new;
150 \&  subtype 'USState'
151 \&      => as Str
152 \&      => where {
153 \&             (    exists $STATES\->{code2state}{ uc($_) }
154 \&               || exists $STATES\->{state2code}{ uc($_) } );
155 \&         };
156 .Ve
157 .PP
158 .Vb 5
159 \&  subtype 'USZipCode'
160 \&      => as Value
161 \&      => where {
162 \&             /^$RE{zip}{US}{\-extended => 'allow'}$/;
163 \&         };
164 .Ve
165 .PP
166 .Vb 4
167 \&  has 'street'   => ( is => 'rw', isa => 'Str' );
168 \&  has 'city'     => ( is => 'rw', isa => 'Str' );
169 \&  has 'state'    => ( is => 'rw', isa => 'USState' );
170 \&  has 'zip_code' => ( is => 'rw', isa => 'USZipCode' );
171 .Ve
172 .PP
173 .Vb 3
174 \&  package Company;
175 \&  use Moose;
176 \&  use Moose::Util::TypeConstraints;
177 .Ve
178 .PP
179 .Vb 3
180 \&  has 'name' => ( is => 'rw', isa => 'Str', required => 1 );
181 \&  has 'address'   => ( is => 'rw', isa => 'Address' );
182 \&  has 'employees' => ( is => 'rw', isa => 'ArrayRef[Employee]' );
183 .Ve
184 .PP
185 .Vb 8
186 \&  sub BUILD {
187 \&      my ( $self, $params ) = @_;
188 \&      if ( @{ $self\->employees || [] } ) {
189 \&          foreach my $employee ( @{ $self\->employees } ) {
190 \&              $employee\->employer($self);
191 \&          }
192 \&      }
193 \&  }
194 .Ve
195 .PP
196 .Vb 8
197 \&  after 'employees' => sub {
198 \&      my ( $self, $employees ) = @_;
199 \&      if ($employees) {
200 \&          foreach my $employee ( @{$employees} ) {
201 \&              $employee\->employer($self);
202 \&          }
203 \&      }
204 \&  };
205 .Ve
206 .PP
207 .Vb 2
208 \&  package Person;
209 \&  use Moose;
210 .Ve
211 .PP
212 .Vb 7
213 \&  has 'first_name' => ( is => 'rw', isa => 'Str', required => 1 );
214 \&  has 'last_name'  => ( is => 'rw', isa => 'Str', required => 1 );
215 \&  has 'middle_initial' => (
216 \&      is        => 'rw', isa => 'Str',
217 \&      predicate => 'has_middle_initial'
218 \&  );
219 \&  has 'address' => ( is => 'rw', isa => 'Address' );
220 .Ve
221 .PP
222 .Vb 9
223 \&  sub full_name {
224 \&      my $self = shift;
225 \&      return $self\->first_name
226 \&          . (
227 \&          $self\->has_middle_initial
228 \&          ? ' ' . $self\->middle_initial . '. '
229 \&          : ' '
230 \&          ) . $self\->last_name;
231 \&  }
232 .Ve
233 .PP
234 .Vb 2
235 \&  package Employee;
236 \&  use Moose;
237 .Ve
238 .PP
239 .Vb 1
240 \&  extends 'Person';
241 .Ve
242 .PP
243 .Vb 2
244 \&  has 'title'    => ( is => 'rw', isa => 'Str',     required => 1 );
245 \&  has 'employer' => ( is => 'rw', isa => 'Company', weak_ref => 1 );
246 .Ve
247 .PP
248 .Vb 4
249 \&  override 'full_name' => sub {
250 \&      my $self = shift;
251 \&      super() . ', ' . $self\->title;
252 \&  };
253 .Ve
254 .SH "DESCRIPTION"
255 .IX Header "DESCRIPTION"
256 This recipe introduces the \f(CW\*(C`subtype\*(C'\fR sugar function from
257 Moose::Util::TypeConstraints. The \f(CW\*(C`subtype\*(C'\fR function lets you
258 declaratively create type constraints without building an entire
259 class.
260 .PP
261 In the recipe we also make use of Locale::US and Regexp::Common
262 to build constraints, showing how constraints can make use of existing
263 \&\s-1CPAN\s0 tools for data validation.
264 .PP
265 Finally, we introduce the \f(CW\*(C`required\*(C'\fR attribute option.
266 .PP
267 The the \f(CW\*(C`Address\*(C'\fR class we define two subtypes. The first uses the
268 Locale::US module to check the validity of a state. It accepts
269 either a state abbreviation of full name.
270 .PP
271 A state will be passed in as a string, so we make our \f(CW\*(C`USState\*(C'\fR type
272 a subtype of Moose's builtin \f(CW\*(C`Str\*(C'\fR type. This is done using the \f(CW\*(C`as\*(C'\fR
273 sugar. The actual constraint is defined using \f(CW\*(C`where\*(C'\fR. This function
274 accepts a single subroutine reference. That subroutine will be called
275 with the value to be checked in \f(CW$_\fR (1). It is expected to return a
276 true or false value indicating whether the value is valid for the
277 type.
278 .PP
279 We can now use the \f(CW\*(C`USState\*(C'\fR type just like Moose's builtin types:
280 .PP
281 .Vb 1
282 \&  has 'state'    => ( is => 'rw', isa => 'USState' );
283 .Ve
284 .PP
285 When the \f(CW\*(C`state\*(C'\fR attribute is set, the value is checked against the
286 \&\f(CW\*(C`USState\*(C'\fR constraint. If the value is not valid, an exception will be
287 thrown.
288 .PP
289 The next \f(CW\*(C`subtype\*(C'\fR, \f(CW\*(C`USZipCode\*(C'\fR, uses
290 Regexp::Common. Regexp::Common includes a regex for validating
291 \&\s-1US\s0 zip codes. We use this constraint for the \f(CW\*(C`zip_code\*(C'\fR attribute.
292 .PP
293 .Vb 5
294 \&  subtype 'USZipCode'
295 \&      => as Value
296 \&      => where {
297 \&             /^$RE{zip}{US}{\-extended => 'allow'}$/;
298 \&         };
299 .Ve
300 .PP
301 Using a subtype instead of requiring a class for each type greatly
302 simplifies the code. We don't really need a class for these types, as
303 they're just strings, but we do want to ensure that they're valid.
304 .PP
305 The type constraints we created are reusable. Type constraints are
306 stored by name in a global registry. This means that we can refer to
307 them in other classes. Because the registry is global, we do recommend
308 that you use some sort of pseudo-namespacing in real applications,
309 like \f(CW\*(C`MyApp.Type.USState\*(C'\fR.
310 .PP
311 These two subtypes allow us to define a simple \f(CW\*(C`Address\*(C'\fR class.
312 .PP
313 Then we define our \f(CW\*(C`Company\*(C'\fR class, which has an address. As we saw
314 in earlier recipes, Moose automatically creates a type constraint for
315 each our classes, so we can use that for the \f(CW\*(C`Company\*(C'\fR class's
316 \&\f(CW\*(C`address\*(C'\fR attribute:
317 .PP
318 .Vb 1
319 \&  has 'address'   => ( is => 'rw', isa => 'Address' );
320 .Ve
321 .PP
322 A company also needs a name:
323 .PP
324 .Vb 1
325 \&  has 'name' => ( is => 'rw', isa => 'Str', required => 1 );
326 .Ve
327 .PP
328 This introduces a new attribute option, \f(CW\*(C`required\*(C'\fR. If an attribute
329 is required, then it must be passed to the class's constructor, or an
330 exception will be thrown. It's important to understand that a
331 \&\f(CW\*(C`required\*(C'\fR attribute can still be false or \f(CW\*(C`undef\*(C'\fR, if its type
332 constraint allows that.
333 .PP
334 The next attribute, \f(CW\*(C`employees\*(C'\fR, uses a \fIparameterized\fR type
335 constraint:
336 .PP
337 .Vb 1
338 \&  has 'employees' => ( is => 'rw', isa => 'ArrayRef[Employee]' );
339 .Ve
340 .PP
341 This constraint says that \f(CW\*(C`employees\*(C'\fR must be an array reference
342 where each element of the array is an \f(CW\*(C`Employee\*(C'\fR object. It's worth
343 noting that an \fIempty\fR array reference also satisfies this
344 constraint.
345 .PP
346 Parameterizable type constraints (or \*(L"container types\*(R"), such as
347 \&\f(CW\*(C`ArrayRef[`a]\*(C'\fR, can be made more specific with a type parameter. In
348 fact, we can arbitrarily nest these types, producing something like
349 \&\f(CW\*(C`HashRef[ArrayRef[Int]]\*(C'\fR. However, you can also just use the type by
350 itself, so \f(CW\*(C`ArrayRef\*(C'\fR is legal. (2)
351 .PP
352 If you jump down to the definition of the \f(CW\*(C`Employee\*(C'\fR class, you will
353 see that it has an \f(CW\*(C`employer\*(C'\fR attribute.
354 .PP
355 When we set the \f(CW\*(C`employees\*(C'\fR for a \f(CW\*(C`Company\*(C'\fR we want to make sure
356 that each of these employee objects refers back to the right
357 \&\f(CW\*(C`Company\*(C'\fR in its \f(CW\*(C`employer\*(C'\fR attribute.
358 .PP
359 To do that, we need to hook into object construction. Moose lets us do
360 this by writing a \f(CW\*(C`BUILD\*(C'\fR method in our class. When your class
361 defined a \f(CW\*(C`BUILD\*(C'\fR method, it will be called immediately after an
362 object construction, but before the object is returned to the caller
363 (3).
364 .PP
365 The \f(CW\*(C`Company\*(C'\fR class uses the \f(CW\*(C`BUILD\*(C'\fR method to ensure that each
366 employee of a company has the proper \f(CW\*(C`Company\*(C'\fR object in its
367 \&\f(CW\*(C`employer\*(C'\fR attribute:
368 .PP
369 .Vb 8
370 \&  sub BUILD {
371 \&      my ( $self, $params ) = @_;
372 \&      if ( $self\->employees ) {
373 \&          foreach my $employee ( @{ $self\->employees } ) {
374 \&              $employee\->employer($self);
375 \&          }
376 \&      }
377 \&  }
378 .Ve
379 .PP
380 The \f(CW\*(C`BUILD\*(C'\fR method is executed after type constraints are checked, so
381 it is safe to assume that \f(CW\*(C`$self\->employees\*(C'\fR will return an array
382 reference, and that the elements of that array will be \f(CW\*(C`Employee\*(C'\fR
383 objects.
384 .PP
385 We also want to make sure that whenever the \f(CW\*(C`employees\*(C'\fR attribute for
386 a \f(CW\*(C`Company\*(C'\fR is changed, we also update the \f(CW\*(C`employer\*(C'\fR for each
387 employee.
388 .PP
389 To do this we can use an \f(CW\*(C`after\*(C'\fR modifier:
390 .PP
391 .Vb 8
392 \&  after 'employees' => sub {
393 \&      my ( $self, $employees ) = @_;
394 \&      if ($employees) {
395 \&          foreach my $employee ( @{$employees} ) {
396 \&              $employee\->employer($self);
397 \&          }
398 \&      }
399 \&  };
400 .Ve
401 .PP
402 Again, as with the \f(CW\*(C`BUILD\*(C'\fR method, we know that the type constraint
403 check has already happened, so we can just check for definedness on the
404 \&\f(CW$employees\fR argument.
405 .PP
406 The \fBPerson\fR class does have demonstrate anything new. It has several
407 \&\f(CW\*(C`required\*(C'\fR attributes. It also has a \f(CW\*(C`predicate\*(C'\fR method, which we
408 first used in recipe 3.
409 .PP
410 The only new feature in the \f(CW\*(C`Employee\*(C'\fR class is the \f(CW\*(C`override\*(C'\fR
411 method modifier:
412 .PP
413 .Vb 4
414 \&  override 'full_name' => sub {
415 \&      my $self = shift;
416 \&      super() . ', ' . $self\->title;
417 \&  };
418 .Ve
419 .PP
420 This is just a sugary alternative to Perl's built in \f(CW\*(C`SUPER::\*(C'\fR
421 feature. However, there is one difference. You cannot pass any
422 arguments to \f(CW\*(C`super\*(C'\fR. Instead, Moose simply passes the same
423 parameters that were passed to the method.
424 .PP
425 A more detailed example of usage can be found in
426 \&\fIt/000_recipes/moose_cookbook_basics_recipe4.t\fR.
427 .SH "CONCLUSION"
428 .IX Header "CONCLUSION"
429 This recipe was intentionally longer and more complex. It illustrates
430 how Moose classes can be used together with type constraints, as well
431 as the density of information that you can get out of a small amount
432 of typing when using Moose.
433 .PP
434 This recipe also introduced the \f(CW\*(C`subtype\*(C'\fR function, the \f(CW\*(C`required\*(C'\fR
435 attribute, and the \f(CW\*(C`override\*(C'\fR method modifier.
436 .PP
437 We will revisit type constraints in future recipes, and cover type
438 coercion as well.
439 .SH "FOOTNOTES"
440 .IX Header "FOOTNOTES"
441 .IP "(1)" 4
442 .IX Item "(1)"
443 The value being checked is also passed as the first argument to
444 the \f(CW\*(C`where\*(C'\fR block, so it can be accessed as \f(CW$_[0]\fR.
445 .IP "(2)" 4
446 .IX Item "(2)"
447 Note that \f(CW\*(C`ArrayRef[]\*(C'\fR will not work. Moose will not parse this as a
448 container type, and instead you will have a new type named
449 \&\*(L"ArrayRef[]\*(R", which doesn't make any sense.
450 .IP "(3)" 4
451 .IX Item "(3)"
452 The \f(CW\*(C`BUILD\*(C'\fR method is actually called by \f(CW\*(C`Moose::Object\->BUILDALL\*(C'\fR, which is called by \f(CW\*(C`Moose::Object\->new\*(C'\fR. The \f(CW\*(C`BUILDALL\*(C'\fR
453 method climbs the object inheritance graph and calls any \f(CW\*(C`BUILD\*(C'\fR
454 methods it finds in the correct order.
455 .SH "AUTHORS"
456 .IX Header "AUTHORS"
457 Stevan Little <stevan@iinteractive.com>
458 .PP
459 Dave Rolsky <autarch@urth.org>
460 .SH "COPYRIGHT AND LICENSE"
461 .IX Header "COPYRIGHT AND LICENSE"
462 Copyright 2006\-2009 by Infinity Interactive, Inc.
463 .PP
464 <http://www.iinteractive.com>
465 .PP
466 This library is free software; you can redistribute it and/or modify
467 it under the same terms as Perl itself.