<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Eric L Anderson.com</title>
	<atom:link href="http://ericlanderson.com/feed" rel="self" type="application/rss+xml" />
	<link>http://ericlanderson.com</link>
	<description></description>
	<lastBuildDate>Sun, 22 Jan 2012 18:49:10 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>Making SSH Fast</title>
		<link>http://ericlanderson.com/entries/making-ssh-fast</link>
		<comments>http://ericlanderson.com/entries/making-ssh-fast#comments</comments>
		<pubDate>Fri, 13 Jan 2012 17:08:40 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Code]]></category>
		<category><![CDATA[Linux]]></category>
		<category><![CDATA[OS X]]></category>
		<category><![CDATA[Tips]]></category>

		<guid isPermaLink="false">http://0xea.com/?p=96</guid>
		<description><![CDATA[In my day to day work, I frequently need to bounce to various SSH servers to see whats happening or put out a fire. Nothing drives me more insane than having to wait 5-10 seconds for SSH. So I put &#8230; <a href="http://ericlanderson.com/entries/making-ssh-fast">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>In my day to day work, I frequently need to bounce to various SSH servers to see whats happening or put out a fire. Nothing drives me more insane than having to wait 5-10 seconds for SSH. So I put together the various pieces in one nice package for you. (Note: this is for mac/linux only)</p>
<p>First, update your <code>~/.ssh/config</code> to be sure that your <code>Host *</code> section has at least this in it:</p>
<div id="gist-1607514" class="gist">

        <div class="gist-file">
          <div class="gist-data gist-syntax">
              <div class="highlight"><pre><div class='line' id='LC1'>Host *</div><div class='line' id='LC2'>	ServerAliveInterval 30</div><div class='line' id='LC3'>	ServerAliveCountMax 2</div><div class='line' id='LC4'>	ControlPath ~/.ssh/master-%r@%h:%p</div><div class='line' id='LC5'>	ControlMaster auto</div></pre></div>
          </div>

          <div class="gist-meta">
            <a href="https://gist.github.com/raw/1607514/27ddeaf8f51aca8f57209a0f01cd29d7f9f5f908/.sshconfig" style="float:right;">view raw</a>
            <a href="https://gist.github.com/1607514#file_.sshconfig" style="float:right;margin-right:10px;color:#666">.sshconfig</a>
            <a href="https://gist.github.com/1607514">This Gist</a> brought to you by <a href="http://github.com">GitHub</a>.
          </div>
        </div>
</div>

<p>Second, add this shell script to your ~/bin or wherever you keep your shell scripts:</p>
<div id="gist-1607514" class="gist">

        <div class="gist-file">
          <div class="gist-data gist-syntax">
              <div class="highlight"><pre><div class='line' id='LC1'><span class="c">#!/bin/bash</span></div><div class='line' id='LC2'><br/></div><div class='line' id='LC3'><span class="nv">SSH_OPTIONS</span><span class="o">=</span><span class="s2">&quot; -MNf&quot;</span></div><div class='line' id='LC4'><br/></div><div class='line' id='LC5'><span class="nb">export </span><span class="nv">AUTOSSH_GATETIME</span><span class="o">=</span>0</div><div class='line' id='LC6'><span class="nb">export </span><span class="nv">AUTOSSH_PORT</span><span class="o">=</span>0</div><div class='line' id='LC7'><br/></div><div class='line' id='LC8'><span class="k">function </span>makefast <span class="o">{</span></div><div class='line' id='LC9'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="nv">HOST</span><span class="o">=</span><span class="nv">$1</span></div><div class='line' id='LC10'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="nb">shift</span></div><div class='line' id='LC11'><span class="nb">        </span><span class="nv">ADDITIONAL_ARGS</span><span class="o">=</span><span class="nv">$@</span></div><div class='line' id='LC12'><br/></div><div class='line' id='LC13'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="nv">CMD</span><span class="o">=</span><span class="s2">&quot;autossh -M 0 -f -- $HOST $SSH_OPTIONS $ADDITIONAL_ARGS&quot;</span></div><div class='line' id='LC14'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="sb">`</span><span class="nv">$CMD</span><span class="sb">`</span></div><div class='line' id='LC15'><span class="o">}</span></div><div class='line' id='LC16'><br/></div><div class='line' id='LC17'>makefast bamboo@bamboo</div><div class='line' id='LC18'>makefast gerrit</div><div class='line' id='LC19'>makefast jira</div></pre></div>
          </div>

          <div class="gist-meta">
            <a href="https://gist.github.com/raw/1607514/e6dd23e8e6bcdf7dc9d65134034edab389274eb6/fastssh.sh" style="float:right;">view raw</a>
            <a href="https://gist.github.com/1607514#file_fastssh.sh" style="float:right;margin-right:10px;color:#666">fastssh.sh</a>
            <a href="https://gist.github.com/1607514">This Gist</a> brought to you by <a href="http://github.com">GitHub</a>.
          </div>
        </div>
</div>

<p>Edit fastssh.sh and add new lines for the servers you connect to. In my above example, I have 3 servers defined &#8220;jira&#8221;, &#8220;gerrit&#8221;, and &#8220;bamboo&#8221;.</p>
<p>If you want to provide additional SSH arguments like port forwarding, just add them after the hostname/username.</p>
<p>Finally, make sure you install <a href="http://www.harding.motd.ca/autossh/">autossh</a>.</p>
<h2>Cool, what does all of this mean?</h2>
<ul>
<li><code>.ssh/config</code>
<ul>
<li><code>ServerAliveInterval: 30</code> &#8211; Check that the connection is alive every 30 seconds.</li>
<li><code>ServerAliveCountMax: 2</code> &#8211; If there are 2 consecutive keep alive failures, kill the connection.</li>
<li><code>ControlPath: ~/.ssh/master-%r@%h:%p</code> &#8211; The location to save persistent connection information.</li>
<li><code>ControlMaster: auto</code> &#8211; If there is a persistent connection, use it. If not, create one.</li>
</ul>
</li>
<li><code>autossh</code> &#8211; This is a tool, that spawns SSH for you and if SSH quits for an irregular reason, relaunches ssh.</li>
</ul>
<p><small><em>Update:</em> Added explanation of some of the configuration and commands below.</small></p>
<p>[<a href="http://news.ycombinator.com/item?id=3461355">Discuss at Hacker News</a>]</p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/making-ssh-fast/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>MS Office in the App Store: The Business Perspective</title>
		<link>http://ericlanderson.com/entries/ms-office-in-the-app-store-the-business-perspective</link>
		<comments>http://ericlanderson.com/entries/ms-office-in-the-app-store-the-business-perspective#comments</comments>
		<pubDate>Fri, 28 Jan 2011 13:33:13 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Business]]></category>
		<category><![CDATA[OS X]]></category>
		<category><![CDATA[Random Thoughts]]></category>

		<guid isPermaLink="false">http://ericanderson.ws/?p=62</guid>
		<description><![CDATA[Microsoft, I hope you’re listening. I’m about to outline every business reason in the world for you to be in the app store. From the Student perspective: Most students need word processing. Fewer need spreadsheets. Fewer still need to give &#8230; <a href="http://ericlanderson.com/entries/ms-office-in-the-app-store-the-business-perspective">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>Microsoft, I hope you’re listening. I’m about to outline every business reason in the world for you to be in the app store.</p>
<h2>From the Student perspective:</h2>
<p>Most students need word processing. Fewer need spreadsheets. Fewer still need to give presentations.</p>
<p>Options: $20-$60 for iWork on the App Store, paid with your itunes account that your parents probably pay for or $150 for MS Office Student Edition.</p>
<p><strong>Winner</strong>: Apple</p>
<h2>From the Small Business perspective:</h2>
<p>Most businesses need word processing and excel. Few need presentations.</p>
<p>Options: $40-$60 for iWork on the App Store or $280 for MS Office for Home and Business.</p>
<p><strong>Winner</strong>: Apple</p>
<h2>From Microsoft’s perspective:</h2>
<p>Best Buy, OfficeMax, Amazon, etc all need to make some profit. From what I can tell from wholesale prices online, most stores will sell you Microsoft products for 15% off. Obviously these companies are still making a profit. I’m guessing that MS sells wholesale at at least 20% off and 30% off wouldn’t be a stretch.</p>
<p>This kills the argument “Microsoft doesn’t want to give Apple 30%”. They give 30% to everyone else for handling their business, Apple would be no different.</p>
<p>But more important for Microsoft is that they are starting to lose the game. There are Macs and iPads in the enterprise. Some companies use Google Docs. The App Store is simple. Its cheap. Unless you absolutely had to get Office, most people will be buying iWork. I can promise you that Apple Store employees will be telling every new Mac buyer that they can get office software for much cheaper in the App Store, rather than buying it in a box from Microsoft.</p>
<p>Options: Continue to have declining business in the Office arena or slash some prices, join the app store, and give Apple 30%.</p>
<p><strong>Winner</strong>: I don’t know what Microsoft will choose, but in the first case, it’ll likely be Apple that wins. In the second case, they both win.</p>
<p>Time will tell.</p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/ms-office-in-the-app-store-the-business-perspective/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>When a computer is not a toy</title>
		<link>http://ericlanderson.com/entries/when-a-computer-is-not-a-toy</link>
		<comments>http://ericlanderson.com/entries/when-a-computer-is-not-a-toy#comments</comments>
		<pubDate>Thu, 17 Jun 2010 23:31:30 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Random Thoughts]]></category>

		<guid isPermaLink="false">http://wordpressdev.local/?p=4</guid>
		<description><![CDATA[My first computer was a 33mhz Compaq POS. It has Windows 3.1, DOS, and QBasic. (Side note: yes, I got started ‘late’). After I played my first game in QBasic and realized that the words on the screen are what &#8230; <a href="http://ericlanderson.com/entries/when-a-computer-is-not-a-toy">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>My first computer was a 33mhz Compaq POS. It has Windows 3.1, DOS, and QBasic. (Side note: yes, I got started ‘late’). After I played my first game in QBasic and realized that the words on the screen are what made the game tick, I was hooked and I have been ever since. I think I tinkered with and hacked every single device I could get my hands on. You name it, if it had a way to get custom software on there, I was going to try it.</p>
<p>This morning I came across an article on <a href="http://lifehacker.com/">Lifehacker</a> about <a href="http://lifehacker.com/5563196/turn-your-old-router-into-a-range+boosting-wi+fi-repeater">converting your router into a wifi repeater</a>, which sounded really cool to me, so I started reading. Unfortunately about halfway down the page I realized I couldn’t care less about this.</p>
<p>Sure, I can reuse that old hardware collecting dust in the garage. But why? To save a few bucks? What happens when I’m at work and my wife is at home with the baby and the thing stops working? Now I’m getting phone calls to do tech support because I saved $100 and can do that one “cool” thing that I never actually needed in the first place.</p>
<p>When I was 13, the hacky free way was always the best way, not because it was free, but because it was fun to tinker. While it is still fun to tinker, some things should just work. My router should just work. My wife, my mom, and my grandma should be able to use it without calling for help.</p>
<p>The same goes for my phone, my “tablet”, and to some extent, my laptop.</p>
<p>The Android argument that you can install whatever you want and that you can even replace the ROM that runs the phone/tablet is insane. 99% of people don’t need that capability. They don’t need the ability to shoot themselves in the foot. I’m sure it would be fun to hack the OS of my iPhone, but at the cost of possibly not making calls? I don’t think so.</p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/when-a-computer-is-not-a-toy/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>How to play turbo hearts</title>
		<link>http://ericlanderson.com/entries/how-to-play-turbo-hearts</link>
		<comments>http://ericlanderson.com/entries/how-to-play-turbo-hearts#comments</comments>
		<pubDate>Fri, 04 Sep 2009 00:00:07 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Games]]></category>
		<category><![CDATA[Turbo Hearts]]></category>

		<guid isPermaLink="false">http://wordpressdev/?p=13</guid>
		<description><![CDATA[The game is a slight variation on regular Hearts, with a few cards having extra meaning, the possibility for a trick to go around twice, and &#8220;special&#8221; cards being &#8220;charged&#8221; (doubling their value). In Turbo Hearts, points are bad. In &#8230; <a href="http://ericlanderson.com/entries/how-to-play-turbo-hearts">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>The game is a slight variation on regular Hearts, with a few cards having extra meaning, the possibility for a trick to go around twice, and &#8220;special&#8221; cards being &#8220;charged&#8221; (doubling their value). In Turbo Hearts, points are bad.</p>
<p>In Turbo Hearts, the <span style="color: green;">10&clubs;</span> doubles your score final score, the <span style="color: teal;">J&diams;</span> gives you -10 points (good), the Q&spades; is worth 13 points, and each heart is worth 1 point.  &#8220;Running&#8221; is defined as taking the Q&spades; and all of the hearts. This is equivilant to &#8220;shooting the moon&#8221; in regular hearts.  Nines are also special in Turbo Hearts; if they are played in suit, they make a trick go around twice.  Charging is a technique that happens before a hand begins that has a few effects:</p>
<ul>
<li>The charged suite is now worth double. A charged Q&spades; is now worth 26pts, a charged <span style="color: red;">A&hearts;</span> makes all hearts worth 2pts, a charged <span style="color: green;">10&clubs;</span> is worth 4x your final score, and a charged <span style="color: teal;">J&diams;</span> is worth -20pts.</li>
<li>The charged card must be placed face up in front of the player until they play it</li>
<li>There is a caviate to charging a card however, you cannot play a charged card on the first trick in suit unless you are forced to do so. An example: You charge the <span style="color: green;">10&clubs;</span> and the only other club you have is the <span style="color: green;">9&clubs;</span>. On the first club trick, you cannot play the <span style="color: green;">10&clubs;</span> since you have another club, so you play your 9, making the trick go around again. Now, you have to play a second time and since your <span style="color: green;">10&clubs;</span> is the only card in suit, you must play that card.</li>
</ul>
<p>The game consists for 4 hands with the flow of the game as follows:</p>
<ol>
<li>Passing &#8211; in order of the 4 hands: 3 left, 3 right, 3 diagonal, no passing.</li>
<li>Charging &#8211; anyone with a chargeable card (<span style="color: green;">10&clubs;</span>, Q&spades;, <span style="color: teal;">J&diams;</span>, <span style="color: red;">A&hearts;</span>) can now charge.</li>
<li>Play starts &#8211; the person with the <span style="color: green;">2&clubs;</span> plays first.</li>
<li>Tricks &#8211; gameplay continues until all tricks have been claimed</li>
<li>Scoring &#8211; scoring is tabulated and saved for later; more details below</li>
</ol>
<p>Scoring may be the most complicated part of playing Turbo Hearts but it is really easy once you get the hang of it. Scoring is performed by totally up everyones points, multiplying if they got the <span style="color: green;">10&clubs;</span>, making negative if they &#8220;ran&#8221; and totally it up with the previous tricks.  We keep a notebook of scores, with each hand taking a line, the hand total on the left and the cumulative sum on the right. Negatives are wrapped in parens. It looks like this:</p>
<table width="400">
<tbody>
<tr>
<th width="25%">RF</th>
<th width="25%">TW</th>
<th width="25%">KB</th>
<th width="25%">EA</th>
</tr>
<tr>
<td>0 &#8211; 0</td>
<td>0 &#8211; 0</td>
<td>72 &#8211; 72</td>
<td>11 &#8211; 11</td>
</tr>
<tr>
<td>16 &#8211; 16</td>
<td>32 &#8211; 32</td>
<td>(10) &#8211; 62</td>
<td>16 &#8211; 27</td>
</tr>
<tr>
<td>12 &#8211; 18</td>
<td>4 &#8211; 45</td>
<td>16 &#8211; 78</td>
<td>16 &#8211; 43</td>
</tr>
<tr>
<td>0 &#8211; 18</td>
<td>0 &#8211; 45</td>
<td>0 &#8211; 78</td>
<td>(248) &#8211; (205)</td>
</tr>
</tbody>
</table>
<p>These are your hand scores and as you can see, I did really well on the last hand (ran for 248 pts!)</p>
<p>These scores are then kept cumulatively across multiple games and multiple players. Your final game score is calculated by &#8220;paying out&#8221;. What this means, is your total number of points, you must pay to all other players (and they must pay to you). It is good to have a low hand score but the opposite is true for a game score; higher scores are better.</p>
<p>So the final games scores are:</p>
<table>
<tbody>
<tr>
<td width="40px">RF</td>
<td>-18*3 + 35 + 78 &#8211; 205 =</td>
<td>&nbsp;-146</td>
</tr>
<tr>
<td>TW</td>
<td>-35*3 + 18 + 78 &#8211; 205 =</td>
<td>&nbsp;-214</td>
</tr>
<tr>
<td>KB</td>
<td>-78*3 + 18 + 35 &#8211; 205=</td>
<td>&nbsp;-386</td>
</tr>
<tr>
<td>EA</td>
<td>205*3 + 18 + 45 + 78 =</td>
<td>&nbsp;756</td>
</tr>
</tbody>
</table>
<p>We keep these numbers are a long term tally. You can just sum up everyones game scores to see their standings.</p>
<p>The best way to think of these game scores is as pennies. In this game, I would be making $7.56 while the others would be paying out $1.46, $2.14, $3.86 respectively.</p>
<p>In my next post, I will lay out some basic strategy, but now you know how to play.</p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/how-to-play-turbo-hearts/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Terminal.app TabNamer released under GPL</title>
		<link>http://ericlanderson.com/entries/terminal-app-tabnamer-released-under-gpl</link>
		<comments>http://ericlanderson.com/entries/terminal-app-tabnamer-released-under-gpl#comments</comments>
		<pubDate>Sat, 29 Aug 2009 00:00:44 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Code]]></category>
		<category><![CDATA[OS X]]></category>
		<category><![CDATA[Project]]></category>

		<guid isPermaLink="false">http://wordpressdev/?p=20</guid>
		<description><![CDATA[Short and sweet, I have no intention of maintaining this code. It seems that snow leopard completely removes the need for it and as such, I am releasing it at github. TabNamer @ GitHub]]></description>
			<content:encoded><![CDATA[<p>Short and sweet, I have no intention of maintaining this code. It seems that snow leopard completely removes the need for it and as such, I am releasing it at github.</p>
<p><a href="http://github.com/EricAnderson/Terminal.app-TabNamer">TabNamer @ GitHub</a></p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/terminal-app-tabnamer-released-under-gpl/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Archiving a message via keyboard shortcut in Microsoft Entourage</title>
		<link>http://ericlanderson.com/entries/archiving-a-message-via-keyboard-shortcut-in-microsoft-entourage</link>
		<comments>http://ericlanderson.com/entries/archiving-a-message-via-keyboard-shortcut-in-microsoft-entourage#comments</comments>
		<pubDate>Fri, 27 Feb 2009 00:00:45 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[AppleScript]]></category>
		<category><![CDATA[OS X]]></category>

		<guid isPermaLink="false">http://wordpressdev/?p=25</guid>
		<description><![CDATA[This has been driving me nuts for a long time and I finally figured out the applescript for this so I figured I should share. The script is: This script assumes you have an exchange account and a folder in &#8230; <a href="http://ericlanderson.com/entries/archiving-a-message-via-keyboard-shortcut-in-microsoft-entourage">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>This has been driving me nuts for a long time and I finally figured out the applescript for this so I figured I should share.</p>
<p>The script is:</p>
<p><script src="https://gist.github.com/760535.js?file=gistfile1.scpt"></script></p>
<p>This script assumes you have an exchange account and a folder in that exchange account you want to use.</p>
<p>If you want to use an archive folder that is a subfolder of another folder, you&rsquo;ll want to tweak the script to say something like &ldquo;to folder archiveFolderName in folder parentFolderName in Exchange account exchangeAccount&rdquo; and add a parentFolderName variable to the top of the script.</p>
<p>Now all you have to do is save the script in: &#8220;<code>~/Documents/Microsoft User Data/Entourage Script Menu Items/Archive\cA</code>&#8220;</p>
<p>This will put it in your script menu and set the keystroke ctrl+a to &ldquo;Archive&rdquo;.</p>
<p>Enjoy!</p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/archiving-a-message-via-keyboard-shortcut-in-microsoft-entourage/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Rant: Using error codes in user messages</title>
		<link>http://ericlanderson.com/entries/rant-using-error-codes-in-user-messages</link>
		<comments>http://ericlanderson.com/entries/rant-using-error-codes-in-user-messages#comments</comments>
		<pubDate>Tue, 05 Aug 2008 00:00:34 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Code]]></category>
		<category><![CDATA[Rant]]></category>

		<guid isPermaLink="false">http://wordpressdev/?p=31</guid>
		<description><![CDATA[In short: DON&#8217;T! What in the world was Apple thinking when you try to upgrade/register/sync your iPhone/iPod and you get &#8220;Error: -19&#8243; or &#8220;Error: -20&#8243;?? What good does this do any one? How am I supposed to fix the problem &#8230; <a href="http://ericlanderson.com/entries/rant-using-error-codes-in-user-messages">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>In short: DON&rsquo;T!</p>
<p>What in the world was Apple thinking when you try to upgrade/register/sync your iPhone/iPod and you get &ldquo;Error: -19&Prime; or &ldquo;Error: -20&Prime;?? What good does this do any one? How am I supposed to fix the problem if I don&rsquo;t know what the problem is? Isn&rsquo;t Apple the king of user-friendliness?</p>
<p>When you write software, you should use good error messages. You should use good exceptions. You should use descriptive values.</p>
<p>Granted, some things the user cannot fix. Telling the user the database connection was lost on a web application does very little good for the user. You can however tell the user that an error that was not their fault occurred. At least then I know I can come back and try again later.</p>
<p>Luckily, after rebooting my iPhone I was able to install the recent software update. This may not have been the problem, but certainly Apple could have notified me that I should attempt rebooting.</p>
<p><strong>In any case, be nice to your damn users!</strong></p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/rant-using-error-codes-in-user-messages/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Using EclEmma to write better unit tests</title>
		<link>http://ericlanderson.com/entries/using-eclemma-to-write-better-unit-tests</link>
		<comments>http://ericlanderson.com/entries/using-eclemma-to-write-better-unit-tests#comments</comments>
		<pubDate>Thu, 08 May 2008 00:00:36 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Code]]></category>
		<category><![CDATA[Code Coverage]]></category>
		<category><![CDATA[Java]]></category>
		<category><![CDATA[Testing]]></category>

		<guid isPermaLink="false">http://wordpressdev/?p=36</guid>
		<description><![CDATA[If you don&#8217;t already write unit tests you should be. (Hey, why aren&#8217;t you writing unit tests?) Unit testing has so many benefits and the upfront developer cost to write some unit tests can pay huge dividends later when you &#8230; <a href="http://ericlanderson.com/entries/using-eclemma-to-write-better-unit-tests">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>If you don&rsquo;t already write unit tests you should be. (Hey, why aren&rsquo;t you writing unit tests?) Unit testing has so many benefits and the upfront developer cost to write some unit tests can pay huge dividends later when you aren&rsquo;t spending time debugging broken code nor attempting to save face due to clueless mistakes. You can also use them as a contract to the expectations of your implementations.</p>
<p>So, assuming you have some unit tests, how useful are they if they don&rsquo;t test everything? At some level you will want to have a good idea that you&rsquo;re testing everything. (NOTE: I mean everything really important. Writing perfect 100% coverage like this would likely be too expensive for the entire codebase.) This is where <a href="http://emma.sourceforge.net/">Emma</a> comes in (and more importantly for us, <a href="http://www.eclemma.org/index.html">EclEmma</a>, an Eclipse plugin for Emma). Emma is a code coverage tool which lets you visual which parts of your code get executed during some execution (regular or JUnit).</p>
<p>Lets walk through using EclEmma to ensure that we have adequate testing being done. Lets test the following two classes.</p>
<p>GuessTheNumber.java:</p>
<div id="gist-760542" class="gist">

        <div class="gist-file">
          <div class="gist-data gist-syntax">
              <div class="highlight"><pre><div class='line' id='LC1'><span class="kn">import</span> <span class="nn">java.util.Random</span><span class="o">;</span></div><div class='line' id='LC2'><br/></div><div class='line' id='LC3'><span class="kd">public</span> <span class="kd">class</span> <span class="nc">GuessTheNumber</span> <span class="o">{</span></div><div class='line' id='LC4'><br/></div><div class='line' id='LC5'>	<span class="kd">private</span> <span class="kd">final</span> <span class="n">Integer</span> <span class="n">value</span><span class="o">;</span></div><div class='line' id='LC6'>	<span class="kd">private</span> <span class="kd">final</span> <span class="kt">int</span> <span class="n">min</span><span class="o">;</span></div><div class='line' id='LC7'>	<span class="kd">private</span> <span class="kd">final</span> <span class="kt">int</span> <span class="n">max</span><span class="o">;</span></div><div class='line' id='LC8'>	<span class="kd">private</span> <span class="kt">int</span> <span class="n">guesses</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span></div><div class='line' id='LC9'>	<span class="kd">private</span> <span class="kt">boolean</span> <span class="n">solved</span> <span class="o">=</span> <span class="kc">false</span><span class="o">;</span></div><div class='line' id='LC10'><br/></div><div class='line' id='LC11'>	<span class="kd">public</span> <span class="nf">GuessTheNumber</span><span class="o">(</span><span class="kt">int</span> <span class="n">min</span><span class="o">,</span> <span class="kt">int</span> <span class="n">max</span><span class="o">,</span> <span class="kt">int</span> <span class="n">value</span><span class="o">)</span> <span class="o">{</span></div><div class='line' id='LC12'>		<span class="k">this</span><span class="o">.</span><span class="na">min</span> <span class="o">=</span> <span class="n">min</span><span class="o">;</span></div><div class='line' id='LC13'>		<span class="k">this</span><span class="o">.</span><span class="na">max</span> <span class="o">=</span> <span class="n">max</span><span class="o">;</span></div><div class='line' id='LC14'>		<span class="k">this</span><span class="o">.</span><span class="na">value</span> <span class="o">=</span> <span class="n">value</span><span class="o">;</span></div><div class='line' id='LC15'>	<span class="o">}</span></div><div class='line' id='LC16'><br/></div><div class='line' id='LC17'>	<span class="kd">public</span> <span class="nf">GuessTheNumber</span><span class="o">(</span><span class="kt">int</span> <span class="n">min</span><span class="o">,</span> <span class="kt">int</span> <span class="n">max</span><span class="o">)</span> <span class="o">{</span></div><div class='line' id='LC18'>		<span class="k">this</span><span class="o">(</span><span class="n">min</span><span class="o">,</span> <span class="n">max</span><span class="o">,</span> <span class="n">getRandomNumber</span><span class="o">(</span><span class="n">min</span><span class="o">,</span> <span class="n">max</span><span class="o">));</span></div><div class='line' id='LC19'><br/></div><div class='line' id='LC20'>	<span class="o">}</span></div><div class='line' id='LC21'><br/></div><div class='line' id='LC22'>	<span class="kd">public</span> <span class="kt">int</span> <span class="nf">guess</span><span class="o">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">)</span> <span class="o">{</span></div><div class='line' id='LC23'>		<span class="k">if</span> <span class="o">(</span><span class="n">solved</span><span class="o">)</span></div><div class='line' id='LC24'>			<span class="k">throw</span> <span class="k">new</span> <span class="nf">IllegalStateException</span><span class="o">();</span></div><div class='line' id='LC25'><br/></div><div class='line' id='LC26'>		<span class="n">guesses</span><span class="o">++;</span></div><div class='line' id='LC27'><br/></div><div class='line' id='LC28'>		<span class="kt">int</span> <span class="n">ret</span> <span class="o">=</span> <span class="n">value</span><span class="o">.</span><span class="na">compareTo</span><span class="o">(</span><span class="n">i</span><span class="o">);</span></div><div class='line' id='LC29'><br/></div><div class='line' id='LC30'>		<span class="k">if</span> <span class="o">(</span><span class="n">ret</span> <span class="o">==</span> <span class="mi">0</span><span class="o">)</span></div><div class='line' id='LC31'>			<span class="n">solved</span> <span class="o">=</span> <span class="kc">true</span><span class="o">;</span></div><div class='line' id='LC32'><br/></div><div class='line' id='LC33'>		<span class="k">return</span> <span class="n">ret</span><span class="o">;</span></div><div class='line' id='LC34'>	<span class="o">}</span></div><div class='line' id='LC35'><br/></div><div class='line' id='LC36'>	<span class="kd">public</span> <span class="kt">void</span> <span class="nf">resetCount</span><span class="o">()</span> <span class="o">{</span></div><div class='line' id='LC37'>		<span class="n">guesses</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span></div><div class='line' id='LC38'>		<span class="n">solved</span> <span class="o">=</span> <span class="kc">false</span><span class="o">;</span></div><div class='line' id='LC39'>	<span class="o">}</span></div><div class='line' id='LC40'><br/></div><div class='line' id='LC41'>	<span class="kd">public</span> <span class="kt">int</span> <span class="nf">getValue</span><span class="o">()</span> <span class="o">{</span></div><div class='line' id='LC42'>		<span class="k">if</span> <span class="o">(</span><span class="n">solved</span> <span class="o">==</span> <span class="kc">false</span><span class="o">)</span></div><div class='line' id='LC43'>			<span class="k">throw</span> <span class="k">new</span> <span class="nf">IllegalStateException</span><span class="o">();</span></div><div class='line' id='LC44'><br/></div><div class='line' id='LC45'>		<span class="k">return</span> <span class="n">value</span><span class="o">;</span></div><div class='line' id='LC46'>	<span class="o">}</span></div><div class='line' id='LC47'><br/></div><div class='line' id='LC48'>	<span class="kd">public</span> <span class="kt">int</span> <span class="nf">getMin</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="n">min</span><span class="o">;</span> <span class="o">}</span></div><div class='line' id='LC49'>	<span class="kd">public</span> <span class="kt">int</span> <span class="nf">getMax</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="n">max</span><span class="o">;</span> <span class="o">}</span></div><div class='line' id='LC50'><br/></div><div class='line' id='LC51'>	<span class="kd">private</span> <span class="kd">static</span> <span class="kt">int</span> <span class="nf">getRandomNumber</span><span class="o">(</span><span class="kt">int</span> <span class="n">min</span><span class="o">,</span> <span class="kt">int</span> <span class="n">max</span><span class="o">)</span> <span class="o">{</span></div><div class='line' id='LC52'>		<span class="k">return</span> <span class="k">new</span> <span class="nf">Random</span><span class="o">().</span><span class="na">nextInt</span><span class="o">(</span><span class="n">max</span> <span class="o">-</span> <span class="n">min</span> <span class="o">+</span> <span class="mi">1</span><span class="o">)</span> <span class="o">+</span> <span class="n">min</span><span class="o">;</span></div><div class='line' id='LC53'>	<span class="o">}</span></div><div class='line' id='LC54'><span class="o">}</span></div></pre></div>
          </div>

          <div class="gist-meta">
            <a href="https://gist.github.com/raw/760542/d03d33603d7f738e1fd484bbf3e83b0f787b974a/GuessTheNumber.java" style="float:right;">view raw</a>
            <a href="https://gist.github.com/760542#file_guess_the_number.java" style="float:right;margin-right:10px;color:#666">GuessTheNumber.java</a>
            <a href="https://gist.github.com/760542">This Gist</a> brought to you by <a href="http://github.com">GitHub</a>.
          </div>
        </div>
</div>

<p>And SequentialStrategy.java:</p>
<div id="gist-760543" class="gist">

        <div class="gist-file">
          <div class="gist-data gist-syntax">
              <div class="highlight"><pre><div class='line' id='LC1'><span class="kd">public</span> <span class="kd">class</span> <span class="nc">SequentialStrategy</span> <span class="o">{</span></div><div class='line' id='LC2'><br/></div><div class='line' id='LC3'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="kd">private</span> <span class="kd">final</span> <span class="n">GuessTheNumber</span> <span class="n">guesser</span><span class="o">;</span></div><div class='line' id='LC4'><br/></div><div class='line' id='LC5'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="kd">public</span> <span class="nf">SequentialStrategy</span><span class="o">(</span><span class="n">GuessTheNumber</span> <span class="n">guesser</span><span class="o">)</span> <span class="o">{</span></div><div class='line' id='LC6'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">this</span><span class="o">.</span><span class="na">guesser</span> <span class="o">=</span> <span class="n">guesser</span><span class="o">;</span></div><div class='line' id='LC7'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC8'><br/></div><div class='line' id='LC9'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="kd">public</span> <span class="kt">int</span> <span class="nf">solve</span><span class="o">()</span> <span class="o">{</span></div><div class='line' id='LC10'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="n">guesser</span><span class="o">.</span><span class="na">getMin</span><span class="o">();</span> <span class="n">i</span><span class="o">&amp;</span><span class="n">lt</span><span class="o">;=</span><span class="n">guesser</span><span class="o">.</span><span class="na">getMax</span><span class="o">();</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span></div><div class='line' id='LC11'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">if</span> <span class="o">(</span><span class="n">guesser</span><span class="o">.</span><span class="na">guess</span><span class="o">(</span><span class="n">i</span><span class="o">)</span> <span class="o">==</span> <span class="mi">0</span><span class="o">)</span></div><div class='line' id='LC12'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">return</span> <span class="n">i</span><span class="o">;</span></div><div class='line' id='LC13'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC14'><br/></div><div class='line' id='LC15'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">throw</span> <span class="k">new</span> <span class="nf">IllegalStateException</span><span class="o">();</span></div><div class='line' id='LC16'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC17'><span class="o">}</span></div></pre></div>
          </div>

          <div class="gist-meta">
            <a href="https://gist.github.com/raw/760543/f7c5e0116af044394e9a7f150f53a78dfb406cd8/SequentialStrategy.java" style="float:right;">view raw</a>
            <a href="https://gist.github.com/760543#file_sequential_strategy.java" style="float:right;margin-right:10px;color:#666">SequentialStrategy.java</a>
            <a href="https://gist.github.com/760543">This Gist</a> brought to you by <a href="http://github.com">GitHub</a>.
          </div>
        </div>
</div>

<p>Finally, we&rsquo;ll write up a basic StrategyTest.java:</p>
<div id="gist-760545" class="gist">

        <div class="gist-file">
          <div class="gist-data gist-syntax">
              <div class="highlight"><pre><div class='line' id='LC1'><span class="kn">import</span> <span class="nn">junit.framework.TestCase</span><span class="o">;</span></div><div class='line' id='LC2'><br/></div><div class='line' id='LC3'><span class="kd">public</span> <span class="kd">class</span> <span class="nc">StrategyTest</span> <span class="kd">extends</span> <span class="n">TestCase</span> <span class="o">{</span></div><div class='line' id='LC4'><br/></div><div class='line' id='LC5'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="kd">public</span> <span class="kt">void</span> <span class="nf">testSequentialStrategy</span><span class="o">()</span> <span class="o">{</span></div><div class='line' id='LC6'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">GuessTheNumber</span> <span class="n">guesser</span> <span class="o">=</span> <span class="k">new</span> <span class="n">GuessTheNumber</span><span class="o">(</span><span class="mi">5</span><span class="o">,</span> <span class="mi">100</span><span class="o">);</span></div><div class='line' id='LC7'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">SequentialStrategy</span> <span class="n">strategy</span> <span class="o">=</span> <span class="k">new</span> <span class="n">SequentialStrategy</span><span class="o">(</span><span class="n">guesser</span><span class="o">);</span></div><div class='line' id='LC8'><br/></div><div class='line' id='LC9'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="kt">int</span> <span class="n">value</span> <span class="o">=</span> <span class="n">strategy</span><span class="o">.</span><span class="na">solve</span><span class="o">();</span></div><div class='line' id='LC10'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">assertEquals</span><span class="o">(</span><span class="n">guesser</span><span class="o">.</span><span class="na">getValue</span><span class="o">(),</span> <span class="n">value</span><span class="o">);</span></div><div class='line' id='LC11'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC12'><span class="o">}</span></div></pre></div>
          </div>

          <div class="gist-meta">
            <a href="https://gist.github.com/raw/760545/46948874d64d2a5dd0f9055d43ae77d1c987f8ce/StrategyTest.java" style="float:right;">view raw</a>
            <a href="https://gist.github.com/760545#file_strategy_test.java" style="float:right;margin-right:10px;color:#666">StrategyTest.java</a>
            <a href="https://gist.github.com/760545">This Gist</a> brought to you by <a href="http://github.com">GitHub</a>.
          </div>
        </div>
</div>

<p>So the question is, how good is our test? If you installed EclEmma, you can right click on your Unit Test in Eclipse, head to &ldquo;Coverage As&rdquo; -&gt; &ldquo;JUnit Test&rdquo;</p>
<p><img src="/wp-content/uploads/2011/01/tumblr_l42zo9ZC0i1qalygt.png.scaled500.png" alt="" title="Run as Coverage" width="500" height="118" class="alignnone size-full wp-image-42" /></p>
<p>This will run your unit test against your code and when complete, highlight the code green, yellow, or red for covered, partially-covered, and not-covered respectively.</p>
<p>According to EclEmma, our code coverage when running StrategyTest is:</p>
<p><img src="/wp-content/uploads/2011/01/tumblr_l42zozRzJ01qalygt.png.scaled500.png" alt="" title="tumblr_l42zozRzJ01qalygt.png.scaled500" width="218" height="40" class="aligncenter size-full wp-image-43" /></p>
<p>Thats not too bad, lets take a look at the output for SequentialStrategy:</p>
<p><img src="/wp-content/uploads/2011/01/tumblr_l42zpskvVm1qalygt.png.scaled500.png" alt="" title="tumblr_l42zpskvVm1qalygt.png.scaled500" width="415" height="238" class="aligncenter size-full wp-image-44" /></p>
<p>We may want to test the IllegalStateException since we currently don&rsquo;t and we are expecting it to happen if we&rsquo;ve guessed everything between min and max and haven&rsquo;t solved the problem. This would ensure if someone else comes in behind us and changes this code, the unit test will fail if they take that out and change it to return, say, Integer.MIN_VALUE.</p>
<p>Lets also take a look at some of GuessTheNumber:</p>
<p><img src="/wp-content/uploads/2011/01/tumblr_l42zqnenJ21qalygt.png.scaled500.png" alt="" title="tumblr_l42zqnenJ21qalygt.png.scaled500" width="319" height="335" class="aligncenter size-full wp-image-45" /></p>
<p>It appears we also want the contract to include an IllegalStateException being thrown if you have already solved the guessing game. It also looks like we don&rsquo;t ever call resetCount() and possibly retest after doing that. We also never check if getValue() fails prior to having a solution.</p>
<p>If we modify the test slightly to:</p>
<div id="gist-760546" class="gist">

        <div class="gist-file">
          <div class="gist-data gist-syntax">
              <div class="highlight"><pre><div class='line' id='LC1'><span class="kn">import</span> <span class="nn">junit.framework.TestCase</span><span class="o">;</span></div><div class='line' id='LC2'><br/></div><div class='line' id='LC3'><span class="kd">public</span> <span class="kd">class</span> <span class="nc">StrategyTest</span> <span class="kd">extends</span> <span class="n">TestCase</span> <span class="o">{</span></div><div class='line' id='LC4'><br/></div><div class='line' id='LC5'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="kd">public</span> <span class="kt">void</span> <span class="nf">testSequentialStrategy</span><span class="o">()</span> <span class="o">{</span></div><div class='line' id='LC6'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">GuessTheNumber</span> <span class="n">guesser</span> <span class="o">=</span> <span class="k">new</span> <span class="n">GuessTheNumber</span><span class="o">(</span><span class="mi">5</span><span class="o">,</span> <span class="mi">100</span><span class="o">);</span></div><div class='line' id='LC7'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">SequentialStrategy</span> <span class="n">strategy</span> <span class="o">=</span> <span class="k">new</span> <span class="n">SequentialStrategy</span><span class="o">(</span><span class="n">guesser</span><span class="o">);</span></div><div class='line' id='LC8'><br/></div><div class='line' id='LC9'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="o">;</span> <span class="n">i</span><span class="o">&amp;</span><span class="n">lt</span><span class="o">;</span><span class="mi">3</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span></div><div class='line' id='LC10'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">try</span> <span class="o">{</span></div><div class='line' id='LC11'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">guesser</span><span class="o">.</span><span class="na">getValue</span><span class="o">();</span></div><div class='line' id='LC12'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">fail</span><span class="o">(</span><span class="s">&quot;An exception should have been thrown&quot;</span><span class="o">);</span></div><div class='line' id='LC13'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC14'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">catch</span> <span class="o">(</span><span class="n">IllegalStateException</span> <span class="n">ex</span><span class="o">)</span> <span class="o">{</span> <span class="cm">/**/</span> <span class="o">}</span></div><div class='line' id='LC15'><br/></div><div class='line' id='LC16'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="kt">int</span> <span class="n">value</span> <span class="o">=</span> <span class="n">strategy</span><span class="o">.</span><span class="na">solve</span><span class="o">();</span></div><div class='line' id='LC17'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">assertEquals</span><span class="o">(</span><span class="n">guesser</span><span class="o">.</span><span class="na">getValue</span><span class="o">(),</span> <span class="n">value</span><span class="o">);</span></div><div class='line' id='LC18'><br/></div><div class='line' id='LC19'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">try</span> <span class="o">{</span></div><div class='line' id='LC20'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">guesser</span><span class="o">.</span><span class="na">guess</span><span class="o">(</span><span class="n">guesser</span><span class="o">.</span><span class="na">getMax</span><span class="o">()</span> <span class="o">+</span> <span class="mi">1</span><span class="o">);</span></div><div class='line' id='LC21'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">fail</span><span class="o">(</span><span class="s">&quot;Shouldn&#39;t reach this point&quot;</span><span class="o">);</span></div><div class='line' id='LC22'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC23'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">catch</span> <span class="o">(</span><span class="n">IllegalStateException</span> <span class="n">ex</span><span class="o">)</span> <span class="o">{</span><span class="cm">/**/</span><span class="o">}</span></div><div class='line' id='LC24'><br/></div><div class='line' id='LC25'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">guesser</span><span class="o">.</span><span class="na">resetCount</span><span class="o">();</span></div><div class='line' id='LC26'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC27'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC28'><br/></div><div class='line' id='LC29'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="kd">public</span> <span class="kt">void</span> <span class="nf">testBadGuessGame</span><span class="o">()</span> <span class="o">{</span></div><div class='line' id='LC30'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">GuessTheNumber</span> <span class="n">guesser</span> <span class="o">=</span> <span class="k">new</span> <span class="n">GuessTheNumber</span><span class="o">(</span><span class="mi">1</span><span class="o">,</span> <span class="mi">10</span><span class="o">,</span> <span class="mi">3000</span><span class="o">);</span></div><div class='line' id='LC31'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">SequentialStrategy</span> <span class="n">strategy</span> <span class="o">=</span> <span class="k">new</span> <span class="n">SequentialStrategy</span><span class="o">(</span><span class="n">guesser</span><span class="o">);</span></div><div class='line' id='LC32'><br/></div><div class='line' id='LC33'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">try</span> <span class="o">{</span></div><div class='line' id='LC34'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">strategy</span><span class="o">.</span><span class="na">solve</span><span class="o">();</span></div><div class='line' id='LC35'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="n">fail</span><span class="o">(</span><span class="s">&quot;Should not reach this point&quot;</span><span class="o">);</span></div><div class='line' id='LC36'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC37'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class="k">catch</span> <span class="o">(</span><span class="n">IllegalStateException</span> <span class="n">ex</span><span class="o">)</span> <span class="o">{</span> <span class="cm">/**/</span> <span class="o">}</span></div><div class='line' id='LC38'>&nbsp;&nbsp;&nbsp;&nbsp;<span class="o">}</span></div><div class='line' id='LC39'><span class="o">}</span></div></pre></div>
          </div>

          <div class="gist-meta">
            <a href="https://gist.github.com/raw/760546/86eb975d35b3883f79b7858df7a579d02ba55273/StrategyTest.java" style="float:right;">view raw</a>
            <a href="https://gist.github.com/760546#file_strategy_test.java" style="float:right;margin-right:10px;color:#666">StrategyTest.java</a>
            <a href="https://gist.github.com/760546">This Gist</a> brought to you by <a href="http://github.com">GitHub</a>.
          </div>
        </div>
</div>

<p>And now our code coverage is:</p>
<p><img src="/wp-content/uploads/2011/01/tumblr_l42zrzRMI61qalygt.png.scaled500.png" alt="" title="tumblr_l42zrzRMI61qalygt.png.scaled500" width="221" height="39" class="aligncenter size-full wp-image-46" /></p>
<p>I know this was a very basic example that really didn&rsquo;t test any complex logic or conditions, but I hope it gives you a good idea of how you can use code coverage to improve your unit tests.</p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/using-eclemma-to-write-better-unit-tests/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Making Terminal.app Easier to Read</title>
		<link>http://ericlanderson.com/entries/making-terminal-app-easier-to-read</link>
		<comments>http://ericlanderson.com/entries/making-terminal-app-easier-to-read#comments</comments>
		<pubDate>Wed, 19 Mar 2008 00:00:07 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[OS X]]></category>
		<category><![CDATA[Tips]]></category>

		<guid isPermaLink="false">http://wordpressdev/?p=54</guid>
		<description><![CDATA[I really like the “Pro” color scheme for Terminal.app but I hate how hard it is to read the bold colors. By complete accident however, I came across this Options Page in Terminal.app: Apparently, you can just click that “Use &#8230; <a href="http://ericlanderson.com/entries/making-terminal-app-easier-to-read">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>I really like the “Pro” color scheme for Terminal.app but I hate how hard it is to read the bold colors. By complete accident however, I came across this Options Page in Terminal.app:</p>
<p><img class="aligncenter size-full wp-image-55" title="tumblr_l42z7qBSqZ1qalygt.png.scaled500" src="/wp-content/uploads/2011/01/tumblr_l42z7qBSqZ1qalygt.png.scaled500.png" alt="" width="374" height="351" /></p>
<p>Apparently, you can just click that “Use bright colors for bold text” checkbox and all of a sudden typing things like ls is no longer painful.  Just thought I’d share the tip.</p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/making-terminal-app-easier-to-read/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Terminal.app TabNamer v0.1 Alpha</title>
		<link>http://ericlanderson.com/entries/terminal-app-tabnamer-v0-1-alpha</link>
		<comments>http://ericlanderson.com/entries/terminal-app-tabnamer-v0-1-alpha#comments</comments>
		<pubDate>Sun, 02 Mar 2008 00:00:43 +0000</pubDate>
		<dc:creator>Eric Anderson</dc:creator>
				<category><![CDATA[Uncategorized]]></category>
		<category><![CDATA[Code]]></category>
		<category><![CDATA[OS X]]></category>
		<category><![CDATA[Project]]></category>

		<guid isPermaLink="false">http://wordpressdev/?p=59</guid>
		<description><![CDATA[This is a SIMBL plugin for Terminal.app on Leopard that lets you name your tabs. Because this is an Alpha, I am not going to write up instructions on where to get SIMBL, how to install it, or how to &#8230; <a href="http://ericlanderson.com/entries/terminal-app-tabnamer-v0-1-alpha">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>This is a SIMBL plugin for Terminal.app on Leopard that lets you name your tabs. Because this is an Alpha, I am not going to write up instructions on where to get SIMBL, how to install it, or how to install the bundle. If you don&rsquo;t already know how, then Alpha software is not for you.</p>
<p>That said, after installing the plugin, press Command+Shift+T to name a tab (or use the Name Tab option under the View menu).</p>
<p>NOTE: This has only been tested on Intel Macs with the latest version of SIMBL. If you have a PowerPC and it works for you, I&rsquo;d love to hear about it in the comments.</p>
<p>Also, due to the nature of me giving this away for free, I cannot guarantee it won&rsquo;t harm your computer, nor can I promise it will fix your marriage. This is for use AT YOUR OWN RISK. I wash my hands completely of responsibility.</p>
<p>Enjoy!</p>
<p><a href="http://github.com/downloads/ericanderson/Terminal.app-TabNamer/tabnamerbundlev01.zip">Terminal Tab Namer v0.1 ALPHA</a></p>
]]></content:encoded>
			<wfw:commentRss>http://ericlanderson.com/entries/terminal-app-tabnamer-v0-1-alpha/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

<!-- Dynamic page generated in 1.843 seconds. -->
<!-- Cached page generated by WP-Super-Cache on 2012-03-31 02:22:32 -->
<!-- Compression = gzip -->
