<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom">
    <title>Modern Perl Programming</title>
    <link rel="alternate" type="text/html" href="http://www.modernperlbooks.com/mt/" />
    <link rel="self" type="application/atom+xml" href="http://www.modernperlbooks.com/mt/atom.xml" />
    <id>tag:www.modernperlbooks.com,2009-01-23:/mt//1</id>
    <updated>2013-05-18T21:05:33Z</updated>
    <subtitle>Perl programming for the modern Perl programmer.
</subtitle>
    <generator uri="http://www.sixapart.com/movabletype/">Movable Type 4.38</generator>

<entry>
    <title>Including People</title>
    <link rel="alternate" type="text/html" href="http://www.modernperlbooks.com/mt/2013/05/including-people.html" />
    <id>tag:www.modernperlbooks.com,2013:/mt//1.541</id>

    <published>2013-05-18T13:00:01Z</published>
    <updated>2013-05-18T21:05:33Z</updated>

    <summary>A conference Code of Conduct can be a positive statement of inclusion, if you look at it that way. Perl&apos;s YAPCs get many things right.</summary>
    <author>
        <name>chromatic</name>
        <uri>http://www.wgz.org/~chromatic</uri>
    </author>
    
    <category term="codeofconduct" label="code of conduct" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="community" label="community" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="conferences" label="conferences" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="perl" label="perl" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="yapc" label="yapc" scheme="http://www.sixapart.com/ns/types#tag" />
    
    <content type="html" xml:lang="en" xml:base="http://www.modernperlbooks.com/mt/">
        <![CDATA[<p>The <a href="http://yapcna.org/">YAPC North America Perl Conferences</a> of
the past couple of years have held an event I like quite a bit. It's the <a
href="http://www.yapcna.org/yn2013/event/1233">first time attendees
mixer</a>.</p>

<p>As of a couple of years ago, YAPC::NA organizers and attendees realized that
about half of the attendees of each conference had never attended a YAPC
before. That's between one and two hundred people whose main face to face
involvement with the larger Perl community may have been limited to a local <a
href="http://pm.org/">Perl Mongers</a> meeting. Yes, these attendees have
almost certainly used the CPAN, very likely participated in a discussion on a
Perl web site, mostly used a Perl mailing list (and not just the YAPC mailing
list), and have probably been on a Perl IRC channel, but they probably aren't
the people you think of when you think "Who are the best connected people in
the Perl community?"</p>

<p>As far back as I can remember (which, admittedly, is one of the YAPC::NAs in Chicago), an early morning talk has served as an <a href="http://www.yapcna.org/yn2013/event/1223">introduction to YAPC</a>, specifically intended to help new attendees understand the conference and its quirks and norms. That talk invites these attendees to the novice welcome meeting.</p>

<p>The organizers also grab as many of the well connected people in the
community&mdash;pumpkings, core developers, CPAN contributors, authors, project
leaders, anyone whose name you might recognize&mdash;and ask them to show up
and be willing to talk to people. That's it.</p>

<p>What I like about this system is that it welcomes people in two ways. First,
it acknowledges that it's okay to be new to YAPC or the Perl community in
person. If that's you, you're not alone. Half of everyone you're going to see
at the conference is like you in that sense.</p>

<p>Not only that, but you have permission to participate. You're welcome to
attend this little meetup that has an explicit place in the schedule&mdash;it's
an official part of the conference&mdash;and you're encouraged to talk to
people you might know only by reputation. They're there to meet and talk to
you. They're not there to hang out in little groups by themselves. They're
there to talk to you.</p>

<p>I've heard good things about this event. I've enjoyed it every time I've
gone. (As an introvert myself, I <em>like</em> having permission to talk to
people with a limit of a couple of hours.)</p>

<p>I feel the same way about a <a
href="http://blog.urth.org/2011/09/05/conference-code-of-conduct-considered-crucial/">YAPC
Code of Conduct</a>. I don't see it as a warning that "straying from a straight
and narrow path of arbitrariness will not be tolerated, so if you're not sure
if you might accidentally say or do something someone else doesn't like, stay
away!" I see it as giving people who aren't necessarily well versed in the
norms and ideals and messy politics of dealing with the Perl community every
day virtually and in person permission to believe that they should feel welcome
and important in the community.</p>

<p>It's about <em>empathy</em>.</p>

<p>I understand people disagree about the wording and even need for a code of conduct, and I don't mean to suggest that such concerns come from robots who lack empathy. By no means.</p>

<p>Yet put yourself in the shoes of someone who feels like he might not quite
fit in in a talk, because it's full of inside jokes and jargon and the kinds of
comfortable banter you only get after you've idled on a handful of Perl IRC
channels for months or years. (Imagine that person's an introvert, or at least
not as stubborn as I am.) Now imagine the speaker or someone else says or does
something that reminds that person that he doesn't belong there, that he
doesn't fit in, that he's different.</p>

<p>That's not necessarily assault. That's not necessarily a criminal act. But
it's probably unnecessary and hopefully unintentional.</p>

<p>(The best silly example I can come up with is a speaker saying "... and of
course, if you're a Windows user, no one cares about you until you man up and
get a real operating system." and half of the audience laughs.)</p>

<p>Sure, there are good legal reasons to have a code of conduct that suggests
that criminal activities such as assault, battery, and sexual assault are
intolerable. There's no gray area about groping or rape or physical
violence.</p>

<p>I agree with a lot of <a
href="http://sushee.no-ip.org/opensourceisnotawarzone.txt">Open source is not a
war zone</a>, and I agree fully that the Perl community is all the richer for
contributions of people like Wendy and Liz and Karen and Su-Shee et cetera. I'm
glad they participate, just like I'm glad people like Tim Bunce and Schwern and
brian d foy and Dave Rolsky and Rik et cetera participate.</p>

<p>I just can't quite agree that a code of conduct has a chilling effect that
will exclude people. I don't see it.</p>

<p>Maybe that's because I see the code of conduct as explicitly saying "If you
feel like you don't quite fit in, that's okay. You're welcome here. We take you
seriously. If you have one of these big problems&mdash;even if it's with a
speaker or writer or developer with a famous name&mdash;we'll take that
seriously. The rules apply to everyone."</p>

<p>Sure, there's more to helping newcomers feel welcome than enforcing a policy
of civil conduct, but that's the minimum I want to see, and I'm glad that YAPCs
have done other things (less controversial, I'm sure) to that end.</p>]]>
        
    </content>
</entry>

<entry>
    <title>Running Named Perl Tests from Prove</title>
    <link rel="alternate" type="text/html" href="http://www.modernperlbooks.com/mt/2013/05/running-named-perl-tests-from-prove.html" />
    <id>tag:www.modernperlbooks.com,2013:/mt//1.540</id>

    <published>2013-05-12T13:00:01Z</published>
    <updated>2013-05-19T20:13:25Z</updated>

    <summary>How to run individual tests in a test file with prove, the Perl testing driver.</summary>
    <author>
        <name>chromatic</name>
        <uri>http://www.wgz.org/~chromatic</uri>
    </author>
    
    <category term="automation" label="automation" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="modernperl" label="modern perl" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="perl" label="perl" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="softwaretesting" label="software testing" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="testing" label="testing" scheme="http://www.sixapart.com/ns/types#tag" />
    
    <content type="html" xml:lang="en" xml:base="http://www.modernperlbooks.com/mt/">
        <![CDATA[<p><a
href="http://www.modernperlbooks.com/mt/2013/05/organizing-perl-test-files.html">Organizing
Perl Test Files</a> showed the basic framework I use for individual test files
written to work with Perl's testing tools. While I gladly take advantage of
frameworks such as <a
href="http://search.cpan.org/perldoc?Test::Class">Test::Class</a> and <a
href="http://search.cpan.org/perldoc?Test::Routine">Test::Routine</a>,
sometimes I need something a little simpler.</p>

<p>The discipline of the organization method I explained in the previous
article offers the benefit of simplicity and some discoverability. It also
allows my team to run only a portion of the test suite as needed.</p>

<p>One of our products has a web interface. We have quite a few tests for this,
but because they run through the whole web stack, they're quite a bit slower
than tests for the business model API directly. (We want to make sure the web
site always works, so we have some exhaustive tests.)</p>

<p>We've divided many of these tests up into discrete files based on
controllers and subsets of controllers. The administrative section has a few
test files. The data sharing section has a few test files. The public section
has a few test files.</p>

<p>Some of these tests take a while to run&mdash;multiple seconds. If you're
working on a bug or a feature in one specific action, waiting more than a
couple of seconds for test results is way too long.</p>

<p>That's where the named functions I use to group related tests come in.
Assume you have a test file testing the admin features, and one of those named
functions is <code>test_admin_console_list_expired_users()</code>. You
<em>could</em> edit the <code>main()</code> function to comment out all of the
other tests. Alternately, add a simple code block to <code>main()</code>:</p>

<pre><code><span class="Statement">sub</span> <span class="Identifier">main</span> {
    <span class="Identifier">my</span> @<span class="Identifier">args</span>  = @<span class="Identifier">_</span>;

    <span class="Statement">if</span> (@<span class="Identifier">args</span>) {
        <span class="Identifier">for</span> <span class="Identifier">my</span> $<span class="Identifier">name</span> (@<span class="Identifier">args</span>) {
            <span class="Identifier">die</span> <span class="Constant">&quot;No test method test_$name\n&quot;</span>
                <span class="Statement">unless</span> <span class="Identifier">my</span> $<span class="Identifier">func</span> = <span class="Identifier">__PACKAGE__</span>-&gt;<span class="Identifier">can</span>( '<span class="Identifier">test_</span>' . $<span class="Identifier">name</span> );
            $<span class="Identifier">func</span>-&gt;();
        }

        <span class="Identifier">done_testing</span>;
        <span class="Identifier">return</span> <span class="Constant">0</span>;
    }

    <span class="Comment"># ... run all tests here</span>

    <span class="Identifier">done_testing</span>;
    <span class="Identifier">return</span> <span class="Constant">0</span>;
}</code></pre>

<p>... which will interpret any arguments passed to this test file as names of
test functions to run. To run only the test function <code>test_admin_console_list_expired_users()</code>, use the <code>prove</code> command line:</p>

<pre><code>$ <strong>prove -l t/web/admin_console.t :: admin_console_list_expired_users</strong></code></pre>

<p>The double-colon tells <code>prove</code> to stop looking for its own
arguments and to pass the following arguments to the test file. With that
invocation, only the requested test will run.</p>

<p>For this strategy to work, your test functions must be independent
<em>within</em> your test files. The data the expired users list test needs to
run must already be in place, untouched by other tests, or the test will fail.
That's good test discipline anyway, though.</p>

<p>This strategy only saves us several seconds every time we use it, but saving
several seconds from asking the question "Does this work?" to getting the
answer is a huge benefit in the moment.</p>

<p>There may be easier ways to handle this, but so far this has met a real need
without forcing us to divide our tests into even finer granularity (more files
to manage and remember) but surely allowing us to run tests at the level we
need most. For any test file which takes longer than two or three seconds to
run in parallel, this has been a huge benefit.</p>]]>
        
    </content>
</entry>

<entry>
    <title>Organizing Perl Test Files</title>
    <link rel="alternate" type="text/html" href="http://www.modernperlbooks.com/mt/2013/05/organizing-perl-test-files.html" />
    <id>tag:www.modernperlbooks.com,2013:/mt//1.539</id>

    <published>2013-05-06T13:00:01Z</published>
    <updated>2013-05-19T20:13:20Z</updated>

    <summary>Perl&apos;s test tools let you decide how to organize your test files. Here&apos;s one good approach.</summary>
    <author>
        <name>chromatic</name>
        <uri>http://www.wgz.org/~chromatic</uri>
    </author>
    
    <category term="modernperl" label="modern perl" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="perl" label="perl" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="testing" label="testing" scheme="http://www.sixapart.com/ns/types#tag" />
    
    <content type="html" xml:lang="en" xml:base="http://www.modernperlbooks.com/mt/">
        <![CDATA[<p>As the <a
href="http://modernperlbooks.com/books/modern_perl/chapter_09.html#testing">Testing
section of the Modern Perl book</a> tries to explain, Perl tests are just Perl
code. Sure, the libraries built on top of <a
href="http://search.cpan.org/perldoc?Test::Builder">Test::Builder</a> extend
your testing toolbox by providing new functions to help you write tests, but
tests are just code.</p>

<p>The first implication of that statement is that, if you know how to write
code, you can write tests.</p>

<p>The second implication of that statement&mdash;one which takes longer to
realize&mdash;is that test code has maintenance costs just like code code
does.</p>

<p>I like using <a
href="http://search.cpan.org/perldoc?Test::Class">Test::Class</a> and <a
href="http://search.cpan.org/perldoc?Test::Routine">Test::Routine</a> when they
make sense, but some tests are easier to write when they start with a little
less ceremony. (I also like to refine and reorganize my tests when better
organization suggests itself.) In those cases, I start with something
simpler:</p>

<pre><code><span class="Comment">#!/usr/bin/env perl</span>

<span class="Identifier">use</span> <span class="Statement">Modern</span>::<span class="Identifier">Perl</span> '<span class="Constant">2013</span>';

<span class="Identifier">use</span> <span class="Statement">Test</span>::<span class="Identifier">More</span>;

<span class="Identifier">use</span> <span class="Identifier">lib</span> '<span class="Identifier">t</span>/<span class="Identifier">lib</span>';

<span class="Identifier">exit</span> <span class="Identifier">main</span>( @<span class="Identifier">ARGV</span> );

<span class="Statement">sub</span> <span class="Identifier">main</span> {
    <span class="Identifier">my</span> @<span class="Identifier">args</span>  = @<span class="Identifier">_</span>;

    <span class="Identifier">test_this</span>();
    <span class="Identifier">test_that</span>();
    <span class="Identifier">test_the_other</span>();

    <span class="Identifier">done_testing</span>;
    <span class="Identifier">return</span> <span class="Constant">0</span>;
}</code></pre>

<p>Every set of test assertions I can collect into a named group is a function.
(You can even use <code>Test::More</code> subtests if you like.) When a
function gets too long&mdash;when I can come up with a new name for a subset of
the behavior under test&mdash;it's time for a new function.</p>

<p>(I write <code>exit main( @ARGV );</code> as the first non-pragma line of
the program so that there are no order-of-initialization concerns from Perl's
compile-time/run-time distinctions. If that means nothing to you, carry on;
it's a subtle thing that almost never causes problems.)</p>

<p>Grouping everything under functions also has the benefit of reminding other
developers that it's okay to write more functions. For example, if every test
for every action in a controller ought to verify access permissions, it's easy
to write a helper function to set up an environment with and without access
permissions to test both ways. (Some of these test functions get promoted to
project-specific test libraries.)</p>

<p>I suspect that the discipline of writing test files as if they were code,
not just scripts, is that it provides a subtle pressure to continue to write
tests as if it were code, with all of the discipline and factoring and
maintenance work that implies. It's easier to take something a little messy and
make it a lot messier, but for me at least it's nice to start with something
clean and leave it at least that clean. (This is probably why dishes pile up in
my office when the dishwasher needs to be emptied.)</p>

<p>Please note that these test names do not necessarily correspond to
individual methods or functional units within the code under test. That is,
just because I might have a method called
<code>analyze_country_performance_metrics()</code>, I don't have a single test
function to test that method. I might have several. I might have none (if other
code tests it adequately). Each test function tests a single, coherent,
nameable feature, like "editing a user account with invalid data" or "exporting
person search to CSV".</p>

<p>This is subtle, but it's important. Think in terms of features you can
discuss with end users. (Perhaps that means I find <code>Test::Class</code> and
its friends more useful for unit-style testing.) This helps you navigate your
way through the test suite and your issue tracker by giving everyone canonical
names to <em>describe</em> tests.</p>

<p>A little structure is valuable. It's easy to set up and to maintain. Yes,
there's a little bit of duplication in calling functions and declaring them,
but the benefit of navigation and nomenclature outweigh that many times over.
The specific structure of your test files doesn't matter as much as that
structure exists and you take advantage of it.</p>

<p>(It also lets you run test functions individually as you're fixing bugs or
adding features, but the mechanics of that are the subject of another
post.)</p>
]]>
        
    </content>
</entry>

<entry>
    <title>SEO Tips for Perl Advocacy</title>
    <link rel="alternate" type="text/html" href="http://www.modernperlbooks.com/mt/2013/04/seo-tips-for-perl-advocacy.html" />
    <id>tag:www.modernperlbooks.com,2013:/mt//1.538</id>

    <published>2013-04-29T13:00:01Z</published>
    <updated>2013-05-19T20:13:16Z</updated>

    <summary>SEO tips for busy techies--not marketers.</summary>
    <author>
        <name>chromatic</name>
        <uri>http://www.wgz.org/~chromatic</uri>
    </author>
    
    <category term="advocacy" label="advocacy" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="perl" label="perl" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="seo" label="SEO" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="seotips" label="seo tips" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="webdevelopment" label="web development" scheme="http://www.sixapart.com/ns/types#tag" />
    
    <content type="html" xml:lang="en" xml:base="http://www.modernperlbooks.com/mt/">
        <![CDATA[<p>A few moments after I posted <a
href="http://www.modernperlbooks.com/mt/2013/04/perl-web-pages-and-search-engines.html">Perl
Web Pages and Search Engines</a>, someone at Big Blue Marble said "You should
explain what you've done technically."</p>

<p>I run a few sites, including this one. I've worked on the technology behind
a few others. We've been working on a short article called <a
href="http://outspeaking.com/words-of-technology/simple-seo-in-ten-minutes.html">Simple SEO Tips (in Ten Minutes)</a> to explain a few easy techniques to help web crawlers
find out exactly what a web page is about and to display it to the people who
could most benefit from it.</p>

<p>It's still a work in progress at the moment, but I've used it those
techniques on several BBM projects so far, including <a
href="http://trendshare.org/">Trendshare</a> and its <a
href="http://trendshare.org/how-to-invest/">investment guide for novice
investors</a>, as well as <a href="http://modernperl.net/">ModernPerl.net</a>,
and even the nascent family recipe site <a
href="http://blenderrecipereviews.com">Blender Recipe Reviews</a>.</p>

<p>I know <a href="http://propaganda.pm/">Propaganda.pm</a> tracks the
performance of Perl advocacy campaigns now. If you have a blog or website or
articles about the Perl programming language, maybe some of these tips will
help you get more and better traffic, help crowd old tutorials and outdated out
of the top search results, and improve the visibility of our favorite
programming language.</p>

<p>Imagine, for example, if every one of the generated pages of <a
href="http://search.cpan.org/">search.cpan.org</a> had the phrase "the Perl
programming language" in it and relevant meta description tags....</p>]]>
        
    </content>
</entry>

<entry>
    <title>Perl Web Pages and Search Engines</title>
    <link rel="alternate" type="text/html" href="http://www.modernperlbooks.com/mt/2013/04/perl-web-pages-and-search-engines.html" />
    <id>tag:www.modernperlbooks.com,2013:/mt//1.537</id>

    <published>2013-04-22T13:00:01Z</published>
    <updated>2013-05-05T18:56:49Z</updated>

    <summary>A little bit of metadata can improve how the world sees Perl.</summary>
    <author>
        <name>chromatic</name>
        <uri>http://www.wgz.org/~chromatic</uri>
    </author>
    
    <category term="advocacy" label="advocacy" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="modernperl" label="modern perl" scheme="http://www.sixapart.com/ns/types#tag" />
    <category term="perl" label="perl" scheme="http://www.sixapart.com/ns/types#tag" />
    
    <content type="html" xml:lang="en" xml:base="http://www.modernperlbooks.com/mt/">
        <![CDATA[<p>While browsing <a href="http://www.slideshare.net/andy.sh/perl7-light">Perl
7, the story of</a>, I noticed that Perl6.org has a HTML <code>&lt;meta
name="description" /&gt;</code> tag. I also noticed that it claimed that "Perl
6 is the next major version of Perl".</p>

<p>(Don't worry; <a
href="https://github.com/perl6/perl6.org/commit/39a9a1152e45ef0909839502c42ca0f5d5f0f0ac">I
fixed that</a>.)</p>

<p>I spent a lot of time in the past year working with family members on
websites. Part of that work required me to learn a lot more about SEO and
usability. (Thank goodness for <a href="http://schema.org/">schema.org</a>, for
example.)</p>

<p>The meta description is highly useful. It allows a search engine to display
a contextually accurate and complete (short) phrase when the engine lists the
page in a result set, rather than a snippet of semi-highlighted keywords taken
out of context. This, of course, can make the result list much more useful for
readers.</p>

<p>(I've spent a lot of time adding this description to the pages here on this
site. I haven't finished. I've noticed it's improved search engine traffic here
and elsewhere though; it's worth it.)</p>

<p>When the inevitable discussion of "How can the active Perl community make
itself and all of its great work more visible to the rest of the Internet?"
comes back in the next two or three months, keep in mind the idea of
robustness: having useful information is important, but presenting that
information in a way that's easy for machines to interpret is just as
important.</p>

<p>(I hope that <a href="http://propaganda.pm/">Propaganda.pm</a> is listening.
I'm glad to see that <a href="http://perl.org/">perl.org</a> is too.)</p>
]]>
        
    </content>
</entry>

</feed>
