<?xml version="1.0" encoding="windows-1252"?>
<node id="622705" title="Refactoring Perl #1 - Extract Method" created="2007-06-22 00:15:12" updated="2007-06-21 20:15:12">
<type id="120">
perlmeditation</type>
<author id="530995">
agianni</author>
<data>
<field name="doctext">
&lt;readmore&gt;
&lt;table width="100%"&gt;&lt;tr&gt;
&lt;td align="left"&gt;
&lt;/td&gt;
&lt;td align="center"&gt;&lt;i&gt;&lt;a href="?node_id=3989&amp;n0=0&amp;BIT=&amp;BIS=+&amp;BH=1&amp;HIT=refactoring+perl&amp;HIS=+&amp;xa=0&amp;a=agianni&amp;nf=0&amp;yr=&amp;mo=&amp;dy=&amp;xs=0&amp;M=1&amp;BET=&amp;BES=+&amp;HET=&amp;HES=+&amp;xr=0&amp;re=N&amp;xpa=0&amp;pa=&amp;go=Search&amp;as_user=530995"&gt;Series Index&lt;/a&gt;&lt;/i&gt;&lt;/td&gt;
&lt;td align="right"&gt;
&lt;i&gt;[node://623470|#2 - Inline Method&amp;gt;]&lt;/i&gt;
&lt;/td&gt;
&lt;/td&gt;
&lt;/tr&gt;&lt;/table&gt;
&lt;/readmore&gt;

&lt;blockquote&gt;&lt;p&gt;You have a code fragment that can be grouped together&lt;/p&gt;
&lt;p&gt;&lt;i&gt;Turn the fragment into a method whose name explains the purpose of the method&lt;/i&gt;&lt;/p&gt;
&lt;p&gt;(&lt;a href="http://www.amazon.com/Refactoring-Improving-Design-Existing-Code/dp/0201485672/"&gt;Fowler&lt;/a&gt;, p.110)&lt;/p&gt;&lt;/blockquote&gt;

&lt;p&gt;
Fowler's first refactoring pattern is probably the most intuitive and the one I use 90% of the time when I'm refactoring. That's part of the reason I'm going through these patterns, because I know there are plenty of other useful ones out there (there are 72 in the book after all).
&lt;/p&gt;

&lt;readmore&gt;
&lt;p&gt;
Here is Fowler's example in Perl code:
&lt;/p&gt;

&lt;code&gt;
sub print_owing{
    my $self = shift;
    my $e = $self-&gt;{_orders}-&gt;elements();
    my $outstanding = 0.0;

    # print banner
    print "**************************\n";
    print "***** Customer Owes ******\n";
    print "**************************\n";

    # calculate outstanding
    while ( $e-&gt;has_more_elements() ){
        my $each = $e-&gt;next_element();
        $outstanding += $each-&gt;get_amount();
    }

    # print details
    print 'name: ', $self-&gt;{_name}, "\n";
    print "amount: $outstanding\n";
}
&lt;/code&gt;

&lt;p&gt;
becomes:
&lt;/p&gt;

&lt;code&gt;
sub print_owing{
    my $self = shift;

    $self-&gt;print_banner();
    my $outstanding = $self-&gt;get_outstanding();
    $self-&gt;print_details( $outstanding );
}

sub print_banner{
    my $self = shift;

    # print banner
    print "**************************\n";
    print "***** Customer Owes ******\n";
    print "**************************\n";
}

sub print_details{
    my $self = shift;
    my $outstanding = shift;

    print 'name: ', $self-&gt;{_name}, "\n";
    print "amount: $outstanding\n";
}

sub get_outstanding{
    my $self = shift;

    my $e = $self-&gt;{_orders}-&gt;elements();
    my $result = 0.0;

    # calculate outstanding
    while ( $e-&gt;has_more_elements() ){
        my $each = $e-&gt;next_element();
        $result += $each-&gt;get_amount();
    }
    return $result;
}
&lt;/code&gt;

&lt;p&gt;
Fowler outlines the intricacies through example in three steps but I won't go into that much detail here because I think it's pretty straight forward. You should really buy &lt;a href="http://www.amazon.com/Refactoring-Improving-Design-Existing-Code/dp/0201485672/"&gt;the book&lt;/a&gt; if you're interested. &lt;a href="http://www.newkenmore.com/perl/refactoring.tar.gz"&gt;The code with tests&lt;/a&gt; include the steps in the refactoring process so you can see the whole thing in Perl.
&lt;/p&gt;

&lt;p&gt;
Instead, I'd like to discuss how I've written the unit tests for the example, as testing is an important part of the refactoring process and writing tests for the refactoring patterns will likely require some decent understanding of Perl unit testing methodologies.
&lt;/p&gt;

&lt;p&gt;
There are three non-standard modules that I use in the tests for this code: &lt;a href="http://search.cpan.org/~simonflk/Test-MockModule/lib/Test/MockModule.pm"&gt;Test::MockModule&lt;/a&gt;, &lt;a href="http://search.cpan.org/~chromatic/Test-MockObject/lib/Test/MockObject.pm"&gt;Test::MockObject&lt;/a&gt; and &lt;a href="http://search.cpan.org/~ssoriche/Test-Output/lib/Test/Output.pm"&gt;Test::Output&lt;/a&gt;. The first two are very useful for working with tests for incomplete modules / classes -- which is the case here -- or situations where you don't want to do a great deal of setup of environmental factors just to test a single method / subroutine. Test::Output is very useful to testing code that generates STDOUT or STDERR as this code does. In order to run these tests, you'll need these three modules. I highly recommend &lt;a href="http://langworth.com/"&gt;Ian Langworth&lt;/a&gt; and &lt;a href="http://perlmonks.org/?sourceid=Mozilla-search&amp;node=chromatic&amp;go_button=Search"&gt;chromatic&lt;/a&gt;'s &lt;a href="http://www.amazon.com/Perl-Testing-Developers-Notebook/dp/0596100922/"&gt;Perl Testing, A Developer's Notebook&lt;/a&gt; if you're not comfortable with writing and maintaining tests.
&lt;/p&gt;


&lt;p&gt;
In the case of the test for Refactoring::ExtractMethod::*, I use Test::MockModule to mock up a &lt;code&gt;new&lt;/code&gt; method rather than include it in the class itself. I also used Test::MockObject to put together a quick and dirty object for the _orders object variable. For the purpose of this example it may be overkill, but this is generally how I like to write my tests: isolate the test to the functionality of the method we are testing. Of course this will come back to bite me in the very next refactoring example, but we'll get to that later :)
&lt;/p&gt;

&lt;p&gt;
For now I'll be keeping one tarball of all of the code and I'll update it when I have additional code to share. I'm not sure that's a good long term option, and I'm open to suggestions -- I might CPAN it if I can maintain momentum here.
&lt;/p&gt;
&lt;/readmore&gt;


&lt;p&gt;
I welcome comments and conversation on all aspects of this example: implementation of the example in Perl, testing methodology, tactics for maintaining this series of posts, what have you.
&lt;/p&gt;

&lt;!-- Node text goes above. Div tags should contain sig only --&gt;
&lt;div class="pmsig"&gt;&lt;div class="pmsig-530995"&gt;
&lt;code&gt;
perl -e 'split//,q{john hurl, pest caretaker}and(map{print @_[$_]}(join(q{},map{sprintf(qq{%010u},$_)}(2**2*307*4993,5*101*641*5261,7*59*79*36997,13*17*71*45131,3**2*67*89*167*181))=~/\d{2}/g));'
&lt;/code&gt;
&lt;/div&gt;&lt;/div&gt;</field>
</data>
</node>
