Added Test::Harness & Test::More to t/lib
[gitmo/moose-presentations.git] / moose-class / slides / index.html
1 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
2         "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
3
4 <html xmlns="http://www.w3.org/1999/xhtml">
5
6 <head>
7 <title>Introduction to Moose</title>
8 <!-- metadata -->
9 <meta name="generator" content="S5" />
10 <meta name="version" content="S5 1.2a2" />
11 <meta name="author" content="Eric A. Meyer" />
12 <meta name="company" content="Complex Spiral Consulting" />
13 <!-- configuration parameters -->
14 <meta name="defaultView" content="slideshow" />
15 <meta name="controlVis" content="hidden" />
16 <!-- style sheet links -->
17 <link rel="stylesheet" href="ui/default/slides.css" type="text/css" media="projection" id="slideProj" />
18 <link rel="stylesheet" href="ui/default/outline.css" type="text/css" media="screen" id="outlineStyle" />
19 <link rel="stylesheet" href="ui/default/print.css" type="text/css" media="print" id="slidePrint" />
20 <link rel="stylesheet" href="ui/default/opera.css" type="text/css" media="projection" id="operaFix" />
21 <!-- embedded styles -->
22 <style type="text/css" media="all">
23 .imgcon {width: 525px; margin: 0 auto; padding: 0; text-align: center;}
24 #anim {width: 270px; height: 320px; position: relative; margin-top: 0.5em;}
25 #anim img {position: absolute; top: 42px; left: 24px;}
26 img#me01 {top: 0; left: 0;}
27 img#me02 {left: 23px;}
28 img#me04 {top: 44px;}
29 img#me05 {top: 43px;left: 36px;}
30 </style>
31 <!-- S5 JS -->
32 <script src="ui/default/slides.js" type="text/javascript"></script>
33 <link rel="stylesheet" href="ui/custom.css" type="text/css" />
34 </head>
35 <body>
36
37 <div class="layout">
38 <div id="controls"><!-- DO NOT EDIT --></div>
39 <div id="currentSlide"><!-- DO NOT EDIT --></div>
40 <div id="header"></div>
41 <div id="footer">
42   <h2>Introduction to Moose</h2>
43 </div>
44 </div>
45
46 <div class="presentation">
47
48 <div class="slide">
49   <h1>Introduction to Moose</h1>
50   <h2>YAPC 2009</h2>
51 </div>
52
53 <div class="slide">
54   <h1>Moose Summed Up</h1>
55
56   <ul>
57     <li><strong>Declarative</strong> OO sugar</li>
58     <li>Introspectable</li>
59     <li>Extensible</li>
60   </ul>
61 </div>
62
63 <div class="slide fake-slide0">
64   <h1>Part 0: Moose Concepts</h1>
65 </div>
66
67 <div class="slide">
68   <h1>Moose background</h1>
69
70   <ul>
71     <li>Moose builds on Perl 5's native OO</li>
72     <li>Borrows ideas from other languages, notably Perl 6</li>
73     <li>Provides semantics for common operations</li>
74   </ul>
75 </div>
76
77 <div class="slide">
78   <h1>Classes</h1>
79
80   <ul>
81     <li>
82       Classes have ...
83       <ul>
84         <li>Attributes</li>
85         <li>Methods</li>
86         <li>Superclasses</li>
87         <li>Method modifiers</li>
88         <li>Constructor and destructor</li>
89         <li>One metaclass object</li>
90       </ul>
91     </li>
92     <li>Classes do roles</li>
93   </ul>
94 </div>
95
96 <div class="slide">
97   <h1>Class Example</h1>
98
99   <pre><code>package Person;
100 <span class="highlight">use Moose;</span></code></pre>
101
102   <ul>
103     <li>Poof, a Moose-based class!</li>
104   </ul>
105 </div>
106
107 <div class="slide">
108   <h1>Attributes</h1>
109
110   <ul>
111     <li>Aka property, slot, field, member variable</li>
112     <li>A piece of data owned by an object</li>
113   </ul>
114 </div>
115
116 <div class="slide">
117   <h1>Attributes</h1>
118
119   <ul>
120     <li>
121       Attributes have ...
122       <ul>
123         <li>Access-control (read-only vs read-write)</li>
124         <li>An optional type</li>
125         <li>Accessor methods</li>
126         <li>Delegation methods</li>
127         <li>Optional default value</li>
128         <li>Many more features</li>
129       </ul>
130     </li>
131     <li>Stored in the object, but don't worry about that</li>
132   </ul>
133 </div>
134
135 <div class="slide">
136   <h1>Attribute Example</h1>
137
138   <pre><code>package Person;
139 use Moose;
140
141 <span class="highlight">has 'first_name' =&gt; ( is =&gt; 'rw' );</span></code></pre>
142
143 </div>
144
145 <div class="slide">
146   <h1>Methods</h1>
147
148   <ul>
149     <li>Nothing fancy here, just Perl subroutines</li>
150   </ul>
151
152   <pre><code>package Person;
153 use Moose;
154
155 <span class="highlight">sub greet { ... }</span></code></pre>
156 </div>
157
158 <div class="slide">
159   <h1>Roles</h1>
160
161   <ul>
162     <li>Classes <strong>do</strong> (or consume) roles</li>
163     <li>Similar to mixins and Java interfaces</li>
164   </ul>
165 </div>
166
167 <div class="slide">
168   <h1>Roles</h1>
169
170   <ul>
171     <li>Like classes, can have attributes, methods, do roles</li>
172     <li>Roles can require methods</li>
173     <li>Roles are composed (flattened) into classes</li>
174   </ul>
175 </div>
176
177 <div class="slide">
178   <h1>Role Example</h1>
179
180 <pre><code>package HasPermissions;
181 <span class="highlight">use Moose::Role;</span>
182
183 has is_admin =&gt; ( is =&gt; 'rw' );</code></pre>
184 </div>
185
186 <div class="slide">
187   <h1>Role Example</h1>
188
189   <p>
190     And then ...
191   </p>
192   
193 <pre><code>package Person;
194 use Moose;
195
196 <span class="highlight">with 'HasPermissions';</span></code></pre>
197 </div>
198
199 <div class="slide">
200   <h1>Method Modifiers</h1>
201
202   <ul>
203     <li>AKA advice</li>
204     <li>&quot;<strong>Before</strong> foo(), do this first&quot;</li>
205     <li>&quot;Do this <strong>after</strong> foo()</li>
206     <li>&quot;Put this code <strong>around</strong> foo()&quot;</li>
207   </ul>
208 </div>
209
210 <div class="slide">
211   <h1>Before &amp; After</h1>
212
213 <pre><code>before 'foo'
214     =&gt; sub { warn 'About to call foo()' };
215
216 after  'foo'
217     =&gt; sub { warn 'Leaving foo()' };</code></pre>
218
219 </div>
220
221 <div class="slide">
222   <h1>Around</h1>
223
224 <pre><code>around 'foo' =&gt; sub {
225     my $real_foo = shift;
226     my $self     = shift;
227
228     warn 'Just before foo()';
229     my @return =
230         $self-&gt;$real_foo( @_, bar =&gt; 42 );
231
232     return ( @return, 'modify return values' );
233 };</code></pre>
234 </div>
235
236 <div class="slide">
237   <h1>Type Constraints</h1>
238
239   <ul>
240     <li>NOT A FULL-BLOWN TYPE SYSTEM!</li>
241     <li>But still darn useful</li>
242     <li>Constrain attribute values</li>
243     <li>Coerce from other types</li>
244   </ul>
245 </div>
246
247 <div class="slide">
248   <h1>Type Constraint Example</h1>
249
250 <pre><code>package Person;
251 use Moose;
252
253 has 'weight' =&gt; ( is =&gt; 'ro', <span class="highlight">isa =&gt; 'Int'</span> );
254
255 # kaboom
256 Person-&gt;new( weight =&gt; 'fat' );</code></pre>
257 </div>
258
259 <div class="slide">
260   <h1>Delegation</h1>
261
262   <ul>
263     <li>Attributes can define delegations</li>
264     <li>Lets you hide some implementation details</li>
265     <li>Fewer objects to chase around</li>
266   </ul>
267 </div>
268
269 <div class="slide">
270   <h1>Delegation</h1>
271
272 <pre><code>package Person;
273 use Moose;
274
275 has 'blog_uri' =&gt; (
276     is      =&gt; 'rw',
277     isa     =&gt; 'URI',
278     <span class="highlight">handles =&gt; { 'blog_hostname' =&gt; 'host' },</span>
279 );
280
281 <span class="highlight">$person->blog_hostname;</span>
282 # really calls $person->blog_uri->host
283 </div>
284
285 <div class="slide">
286   <h1>Constructors</h1>
287
288   <ul>
289     <li>Moose creates <code>new()</code> for you</li>
290     <li>Provide an optional <code>BUILDARGS()</code> and <code>BUILD()</code></li>
291   </ul>
292 </div>
293
294 <div class="slide">
295   <h1>Destructors</h1>
296
297   <ul>
298     <li>Provide an optional <code>DEMOLISH()</code></li>
299   </ul>
300 </div>
301
302 <div class="slide">
303   <h1>Moose Meta-API</h1>
304
305   <ul>
306     <li>Answers questions like ...
307       <ul>
308         <li>What methods does this class have?</li>
309         <li>What are its parents?</li>
310         <li>What attributes does it have (including inherited attributes)?</li>
311         <li>What roles does it do?</li>
312         <li>Much, much, more</li>
313       </ul>
314     </li>
315   </ul>
316 </div>
317
318 <div class="slide">
319   <h1>Moose Meta-API</h1>
320
321   <ul>
322     <li>Not just for introspection ...
323       <ul>
324         <li>Add methods, attributes, roles, etc</li>
325         <li>Extend and alter core features</li>
326       </ul>
327     </li>
328   </ul>
329 </div>
330
331 <div class="slide">
332   <h1>Why Moose?</h1>
333
334   <ul>
335     <li>A quick bit of propoganda ...</li>
336   </ul>
337 </div>
338
339 <div class="slide">
340   <h1>With Moose</h1>
341
342   <pre><code>package Person;
343 use Moose;
344
345 has last_name =&gt; (
346     is  =&gt; 'rw',
347     isa =&gt; 'Str',
348 );</code></pre>
349 </div>
350
351 <div class="slide">
352     <h1>Without Moose</h1>
353
354     <pre class="small"><code>package Person;
355 use strict;
356 use warnings;
357 use Carp 'confess';
358
359 sub new {
360     my $class = shift;
361     my %args  = @_;
362     my $self  = {};
363
364     if (exists $args{last_name}) {
365         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
366                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
367             if ref($args{last_name});
368         $self-&gt;{last_nane} = $args{last_name};
369     }
370
371     return bless $self, $class;
372 }
373
374 sub last_name {
375     my $self = shift;
376
377     if (@_) {
378         my $value = shift;
379         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
380                 . &quot;Validation failed for 'Str' with value $value&quot;
381             if ref($value);
382         $self-&gt;{last_name} = $value;
383     }
384
385     return $self-&gt;{last_name};
386 }</code></pre>
387
388 </div>
389
390 <div class="slide">
391     <h1>Side by side</h1>
392
393     <table class="side-by-side">
394         <tr>
395           <td>
396             <pre><code>package Person;
397 use Moose;
398
399 has last_name =&gt; (
400     is  =&gt; 'rw',
401     isa =&gt; 'Str',
402 );</code></pre>
403             </td>
404             <td>
405                 <pre class="small"><code>package Person;
406 use strict;
407 use warnings;
408 use Carp 'confess';
409
410 sub new {
411     my $class = shift;
412     my %args  = @_;
413     my $self  = {};
414
415     if (exists $args{last_name}) {
416         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
417                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
418             if ref($args{last_name});
419         $self-&gt;{last_nane} = $args{last_name};
420     }
421
422     return bless $self, $class;
423 }
424
425 sub last_name {
426     my $self = shift;
427
428     if (@_) {
429         my $value = shift;
430         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
431                 . &quot;Validation failed for 'Str' with value $value&quot;
432             if ref($value);
433         $self-&gt;{last_name} = $value;
434     }
435
436     return $self-&gt;{last_name};
437 }</code></pre>
438             </td>
439         </tr>
440     </table>
441
442 </div>
443
444 <div class="slide">
445     <h1>Side by side</h1>
446
447     <table class="side-by-side">
448         <tr>
449             <td>
450                 <pre><code><span class="match-moose">package Person;</span>
451 use Moose;
452
453 has last_name =&gt; (
454     is  =&gt; 'rw',
455     isa =&gt; 'Str',
456 );</code></pre>
457             </td>
458             <td>
459                 <pre class="small"><code><span class="match-unsweet">package Person;</span>
460 use strict;
461 use warnings;
462 use Carp 'confess';
463
464 sub new {
465     my $class = shift;
466     my %args  = @_;
467     my $self  = {};
468
469     if (exists $args{last_name}) {
470         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
471                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
472             if ref($args{last_name});
473         $self-&gt;{last_nane} = $args{last_name};
474     }
475
476     return bless $self, $class;
477 }
478
479 sub last_name {
480     my $self = shift;
481
482     if (@_) {
483         my $value = shift;
484         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
485                 . &quot;Validation failed for 'Str' with value $value&quot;
486             if ref($value);
487         $self-&gt;{last_name} = $value;
488     }
489
490     return $self-&gt;{last_name};
491 }</code></pre>
492             </td>
493         </tr>
494     </table>
495 </div>
496
497 <div class="slide">
498     <h1>Side by side</h1>
499
500     <table class="side-by-side">
501         <tr>
502             <td>
503                 <pre><code>package Person;
504 <span class="match-moose">use Moose;</span>
505
506 has last_name =&gt; (
507     is  =&gt; 'rw',
508     isa =&gt; 'Str',
509 );</code></pre>
510             </td>
511             <td>
512                 <pre class="small"><code>package Person;
513 <span class="match-unsweet">use strict;
514 use warnings;
515 use Carp 'confess';
516
517 sub new {
518     my $class = shift;
519     my %args  = @_;
520     my $self  = {};</span>
521
522     if (exists $args{last_name}) {
523         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
524                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
525             if ref($args{last_name});
526         $self-&gt;{last_nane} = $args{last_name};
527     }
528
529     <span class="match-unsweet">return bless $self, $class;
530 }</span>
531
532 sub last_name {
533     my $self = shift;
534
535     if (@_) {
536         my $value = shift;
537         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
538                 . &quot;Validation failed for 'Str' with value $value&quot;
539             if ref($value);
540         $self-&gt;{last_name} = $value;
541     }
542
543     return $self-&gt;{last_name};
544 }</code></pre>
545             </td>
546         </tr>
547     </table>
548 </div>
549
550 <div class="slide">
551     <h1>Side by side</h1>
552
553     <table class="side-by-side">
554         <tr>
555             <td>
556                 <pre><code>package Person;
557 use Moose;
558
559 <span class="match-moose">has last_name =&gt; (</span>
560     is  =&gt; 'rw',
561     isa =&gt; 'Str',
562 <span class="match-moose">);</span></code></pre>
563             </td>
564             <td>
565                 <pre class="small"><code>package Person;
566 use strict;
567 use warnings;
568 use Carp 'confess';
569
570 sub new {
571     my $class = shift;
572     my %args  = @_;
573     my $self  = {};
574
575     <span class="match-unsweet">if (exists $args{last_name}) {</span>
576         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
577                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
578             if ref($args{last_name});
579         <span class="match-unsweet">$self-&gt;{last_nane} = $args{last_name};
580     }</span>
581
582     return bless $self, $class;
583 }
584
585 sub last_name {
586     my $self = shift;
587
588     if (@_) {
589         my $value = shift;
590         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
591                 . &quot;Validation failed for 'Str' with value $value&quot;
592             if ref($value);
593         $self-&gt;{last_name} = $value;
594     }
595
596     return $self-&gt;{last_name};
597 }</code></pre>
598             </td>
599         </tr>
600     </table>
601 </div>
602
603 <div class="slide">
604     <h1>Side by side</h1>
605
606     <table class="side-by-side">
607         <tr>
608             <td>
609                 <pre><code>package Person;
610 use Moose;
611
612 has last_name =&gt; (
613     <span class="match-moose">is  =&gt; 'rw',</span>
614     isa =&gt; 'Str',
615 );</code></pre>
616             </td>
617             <td>
618                 <pre class="small"><code>package Person;
619 use strict;
620 use warnings;
621 use Carp 'confess';
622
623 sub new {
624     my $class = shift;
625     my %args  = @_;
626     my $self  = {};
627
628     if (exists $args{last_name}) {
629         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
630                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
631             if ref($args{last_name});
632         $self-&gt;{last_nane} = $args{last_name};
633     }
634
635     return bless $self, $class;
636 }
637
638 <span class="match-unsweet">sub last_name {
639     my $self = shift;
640
641     if (@_) {
642         my $value = shift;</span>
643         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
644                 . &quot;Validation failed for 'Str' with value $value&quot;
645             if ref($value);
646         <span class="match-unsweet">$self-&gt;{last_name} = $value;
647     }
648
649     return $self-&gt;{last_name};
650 }</span></code></pre>
651             </td>
652         </tr>
653     </table>
654 </div>
655
656 <div class="slide">
657     <h1>Side by side</h1>
658
659     <table class="side-by-side">
660         <tr>
661             <td>
662                 <pre><code>package Person;
663 use Moose;
664
665 has last_name =&gt; (
666     is  =&gt; 'rw',
667     <span class="match-moose">isa =&gt; 'Str',</span>
668 );</code></pre>
669             </td>
670             <td>
671                 <pre class="small"><code>package Person;
672 use strict;
673 use warnings;
674 use Carp 'confess';
675
676 sub new {
677     my $class = shift;
678     my %args  = @_;
679     my $self  = {};
680
681     if (exists $args{last_name}) {
682         <span class="match-unsweet">confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
683                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
684             if ref($args{last_name});</span>
685         $self-&gt;{last_nane} = $args{last_name};
686     }
687
688     return bless $self, $class;
689 }
690
691 sub last_name {
692     my $self = shift;
693
694     if (@_) {
695         my $value = shift;
696         <span class="match-unsweet">confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
697                 . &quot;Validation failed for 'Str' with value $value&quot;
698             if ref($value);</span>
699         $self-&gt;{last_name} = $value;
700     }
701
702     return $self-&gt;{last_name};
703 }</code></pre>
704             </td>
705         </tr>
706     </table>
707 </div>
708
709 <div class="slide">
710     <h1>Side by side</h1>
711
712     <table class="side-by-side">
713         <tr class="incremental">
714             <td>5 lines</td>
715             <td>21 lines</td>
716         </tr>
717         <tr class="incremental">
718             <td>92 characters</td>
719             <td>741 characters</td>
720         </tr>
721         <tr>
722             <td>
723                 <pre><code>package Person;
724 use Moose;
725
726 has last_name =&gt; (
727     is  =&gt; 'rw',
728     isa =&gt; 'Str',
729 );</code></pre>
730             </td>
731             <td>
732                 <pre class="small"><code>package Person;
733 use strict;
734 use warnings;
735 use Carp 'confess';
736
737 sub new {
738     my $class = shift;
739     my %args  = @_;
740     my $self  = {};
741
742     if (exists $args{last_name}) {
743         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
744                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
745             if ref($args{last_name});
746         $self-&gt;{last_nane} = $args{last_name};
747     }
748
749     return bless $self, $class;
750 }
751
752 sub last_name {
753     my $self = shift;
754
755     if (@_) {
756         my $value = shift;
757         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
758                 . &quot;Validation failed for 'Str' with value $value&quot;
759             if ref($value);
760         $self-&gt;{last_name} = $value;
761     }
762
763     return $self-&gt;{last_name};
764 }</code></pre>
765             </td>
766         </tr>
767     </table>
768 </div>
769
770 <div class="slide">
771     <h1>Typo?</h1>
772
773     <pre class="small"><code>sub new {
774     my $class = shift;
775     my %args  = @_;
776     my $self  = {};
777
778     if (exists $args{last_name}) {
779         confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
780                 . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
781             if ref($args{last_name});
782         $self-&gt;{last_nane} = $args{last_name};
783     }
784
785     return bless $self, $class;
786 }</code></pre>
787 </div>
788
789 <div class="slide">
790     <h1>Typo?</h1>
791
792     <pre class="small"><code>if (exists $args{last_name}) {
793     confess &quot;Attribute (last_name) does not pass the type constraint because: &quot;
794             . &quot;Validation failed for 'Str' with value $args{last_name}&quot;
795         if ref($args{last_name});
796     $self-&gt;{last_nane} = $args{last_name};
797 }</code></pre>
798 </div>
799
800 <div class="slide">
801     <h1>Typo?</h1>
802
803     <code>$self-&gt;{last_nane} = $args{last_name};</code>
804 </div>
805
806 <div class="slide">
807     <h1>Typo?</h1>
808     <code>$self-&gt;{last_na<span class="highlight">n</span>e}</code>
809 </div>
810
811 <div class="slide">
812     <h1>Why Moose?</h1>
813
814     <pre><code>package Person;
815 use Moose;
816
817 has last_name =&gt; (
818     is  =&gt; 'rw',
819     isa =&gt; 'Str',
820 );</code></pre>
821 </div>
822
823 <div class="slide fake-slide0">
824   <h1>Part 1: Moose Classes</h1>
825 </div>
826
827 <div class="slide">
828   <h1>Moose Classes</h1>
829
830   <ul>
831     <li>Moose classes are Perl packages which <code>use Moose</code></li>
832   </ul>
833 </div>
834
835 <div class="slide">
836   <h1>Moose.pm and Your Class</h1>
837
838   <pre><code>package Person;
839 use Moose;</code></pre>
840
841   <ul>
842     <li><code>Moose.pm</code> provides declarative sugar</li>
843     <li>Turns on <code>strict</code> and <code>warnings</code></li>
844     <li>Creates metaclasses for your class: <code>Person-&gt;meta</code></li>
845     <li>Moose classes automatically inherit from <code>Moose::Object</code></li>
846   </ul>
847 </div>
848
849 <div class="slide">
850   <h1>What <code>Moose::Object</code> Provides</h1>
851
852   <ul>
853     <li>Constructor - <code>new()</code></li>
854     <li>Calls your <code>BUILDARGS()</code> and/or <code>BUILD()</code></li>
855     <li>Calls your <code>DEMOLISH</code> during object destruction</li>
856   </ul>
857 </div>
858
859 <div class="slide">
860   <h1>extends</h1>
861
862   <ul>
863     <li><code>extends</code> is sugar for declaring parent classes</li>
864   </ul>
865
866   <pre><code>package Employee;
867 use Moose;
868 <span class="highlight">extends 'Person';</span></code></pre>
869 </div>
870
871 <div class="slide">
872   <h1>extends</h1>
873
874   <ul>
875     <li>Each call to <code>extends</code> <strong>resets</strong> your parents</li>
876   </ul>
877
878   <h2 class="wrong">WRONG</h2>
879
880   <pre><code>package EvilEmployee;
881 use Moose;
882 extends 'Person';
883 extends 'Thief';</pre></code>
884
885   <h2 class="right">RIGHT</h2>
886
887   <pre><code>package EvilEmployee;
888 use Moose;
889 extends 'Person', 'Thief';</pre></code>
890 </div>
891
892 <div class="slide">
893   <h1>Extending un-Moose-y Parents</h1>
894
895   <pre><code>package My::LWP;
896 use Moose;
897 extends 'LWP';</pre></code>
898
899   <ul>
900     <li>No <code>Moose::Object</code>, so ...
901       <ul>
902         <li>No attribute-handling <code>new()</code></li>
903         <li>No <code>BUILDARGS()</code> or <code>BUILD()</code></li>
904         <li>No <code>DEMOLISH()</code></li>
905       </ul>
906     </li>
907     <li>But see <code>MooseX::NonMoose</code> for a workaround</li>
908   </ul>
909 </div>  
910
911 <div class="slide">
912   <h1><code>overrides</code> and <code>super</code></h1>
913
914   <ul>
915     <li><code>overrides</code> is another method modifier</li>
916     <li>An alternative to Perl's <code>SUPER::</code></li>
917   </ul>
918 </div>
919
920 <div class="slide">
921   <h1><code>overrides</code> and <code>super</code></h1>
922
923   <pre><code>package Employee;
924 use Moose;
925
926 <span class="incremental current">extends 'Person';</span>
927
928 <span class="incremental">overrides</span> work =&gt; sub {
929     my $self = shift;
930
931     die "Pay me first" unless $self-&gt;got_paid;
932     <span class="incremental">super();</span>
933 }<span class="incremental">;</span></code></pre>
934
935 <div class="slide">
936   <h1>Caveat <code>super</code></h1>
937
938   <ul>
939     <li>Mostly like <code>$self-&gt;SUPER::work(@_)</code></li>
940     <li><strong>But</strong> cannot change <code>@_</code>!</li>
941     <li>Binds the parent's method at compile time</li>
942   </ul>
943 </div>
944
945 <div class="slide">
946   <h1>Attributes (Part 1)</h1>
947
948   <ul>
949     <li><code>has 'foo'</code></li>
950     <li>Use <code>is =&gt; 'ro'</code> or <code>is =&gt; 'rw'</code></li>
951     <li>Attributes without "is" have no accessors</li>
952   </ul>
953 </div>
954
955 <div class="slide">
956   <h1>Read-write attributes</h1>
957
958   <pre><code>package Person;
959 use Moose;
960
961 has 'first_name' =&gt; ( <span class="highlight">is =&gt; 'rw'</span> );
962
963 my $person =
964     Person-&gt;new( first_name =&gt; 'Dave' );
965
966 $person-&gt;first_name('Stevan');
967 print $person-&gt;first_name; # Stevan</code></pre>
968
969 </div>
970
971 <div class="slide">
972   <h1>Read-only attributes</h1>
973
974   <pre><code>package Person;
975 use Moose;
976
977 has 'first_name' =&gt; ( <span class="highlight">is =&gt; 'ro'</span> );
978
979 my $person =
980     Person-&gt;new( first_name =&gt; 'Dave' );
981
982 $person-&gt;first_name('Stevan');
983 print $person-&gt;first_name; # Dave</code></pre>
984
985 </div>
986
987 <div class="slide">
988   <h1>There is More to Come</h1>
989
990   <ul>
991     <li>Attributes have a <em>lot</em> of features</li>
992   </ul>
993 </div>
994
995 <div class="slide">
996   <h1>Cleaning Up Moose Droppings</h1>
997
998   <pre><code>package Person;
999 use Moose;
1000
1001 # true
1002 Person->can('extends');</code></pre>
1003
1004   <ul>
1005     <li>Not very hygienic</li>
1006   </ul>
1007 </div>
1008
1009 <div class="slide">
1010   <h1>Cleaning Up Moose Droppings</h1>
1011
1012   <pre><code>package Person;
1013 use Moose;
1014
1015 ...
1016
1017 no Moose;
1018
1019 # false
1020 Person->can('extends');</code></pre>
1021 </div>
1022
1023 <div class="slide">
1024   <h1>No Moose</h1>
1025
1026   <ul>
1027     <li><code>no Moose</code> at the end of a package is a best practice</li>
1028     <li>Just do it</li>
1029   </ul>
1030 </div>
1031
1032 <div class="slide">
1033   <h1>Immutability</h1>
1034
1035   <ul>
1036     <li><span style="font-family: URW Chancery L; font-size: 140%">Stevan's Incantation of Fleet-Footedness</span></li>
1037   </ul>
1038
1039   <pre><code>package Person;
1040 use Moose;
1041
1042 <span class="highlight">__PACKAGE__->meta->make_immutable;</span></code></pre>
1043 </div>
1044
1045 <div class="slide">
1046   <h1>What <code>make_immutable</code> does</h1>
1047
1048   <ul>
1049     <li>Magic</li>
1050     <li>Uses <code>eval</code> to "inline" a constructor</li>
1051     <li>Memoizes a lot of meta-information</li>
1052     <li>Makes loading your class slower</li>
1053     <li>Makes object creation <em>much</em> faster</li>
1054   </ul>
1055 </div>
1056
1057 <div class="slide">
1058   <h1>When to Immutabilize?</h1>
1059
1060   <ul>
1061     <li><em>Almost</em> always</li>
1062     <li>Startup time vs execution time</li>
1063   </ul>
1064 </div>
1065
1066 <div class="slide">
1067   <h1>Exercises</h1>
1068
1069   <pre>$ cd exercises
1070 $ perl bin/prove -lv t/00-prereq.t
1071
1072 Missing anything? Install it. (see tarballs/)
1073
1074 # perl bin/prove -lv t/01-classes.t
1075
1076 Iterate til this passes all its tests
1077
1078 </body>
1079 </html>