Monthly Archives: February 2009

Five unit testing tips #4: Don’t mock your way into accidental complexity

I’ve all but stopped using mock objects in my tests. The reason is that mocking have had a detrimental effect on the design of my systems. I’ve often ended up having the mocks trick me into adding a needless layer of indirection that does nothing except delegate to the next layer, just to satisfy the mocks.

For a while, I was wondering whether I was the only one with this problem, but then I saw this tutorial on JBehave, which so perfectly illustrates the problem I saw myself doing. Now, I don’t mean to pick on JBehave, or the author of this tutorial. Furthermore, this is not a particularly extreme example of the problem. Rather, the point of this posting is to show that even expert developers run into this trap.

Here is the test from the JBehave tutorial:

@Test
public void shouldProvideNotesToBePlayedInOrder() {
    TabParser parser = mock(TabParser.class);
    String asciiTab = "e|--------A3-B6-";
 
    List<note> notes = asList(A(3), B(6));
    stub(parser.parse(asciiTab)).toReturn(notes);
 
    Tab tab = new Tab(asciiTab, parser);
 
    List</note><note> actualNotes = tab.notesToBePlayed();
 
    ensureThat(notes, equalTo(actualNotes));
}
</note>

In other words, the tab’s notes to be played should be equal to the parsed notes.

Here’s the implementation:

public class Tab {
 
    private final List<note> notes;
 
    public Tab(String asciiTab,
               TabParser parser) {
        notes = parser.parse(asciiTab);
    }
 
    public List</note><note> notesToBePlayed() {
        return notes;
    }
}
</note>

Whoops! We just introduced a layer in the design that does nothing. As a matter of fact, removing the Tab class from the whole example leaves us with a design that’s easier to understand.

Mocks can be great when you really, really need them. And I’m extremely impressed by the power of mockito. But used inappropriately, mocking can trick you into creating accidental complexity and extra layers of code that does nothing.

Posted in English, Java, Software Development | 6 Comments

… but please do repeat me

The hard choice between duplication, paralysis and chaos

A common programmer credo is “Don’t Repeat Yourself” (Pragmatic Programmer) or “Once and only once” (Extreme Programming). Like all credos, we risk following it even when it is not appropriate.

The larger truth is that we have choice between three evils:

  • We can duplicate our code, thus duplicating effort, understanding and being forced to hunt down twice.
  • We can share code and affect everyone who shares the code every time we change to code to better fit our needs. If this is a large number of people, this translates into lots of extra work. If you’re on a large project, you might’ve experienced code storms: Days where you’re unable to get any work done as you’re chasing the consequences of other people’s changes.
  • We can keep shared code unchanging, thus forgoing improvements. Most code I (and I expect, you) write is not initially fit for its purpose, so this means leaving bad code to cause more harm.

I expect there is no perfect answer to this dilemma. When the number of people involved is low, we might accept the noise of people changing code that’s used by others. As the number of people in a project grows, this becomes increasingly painful to everyone involved. At some time, large projects start experiencing paralysis.

If we’re not happy with the state of the code when paralysis sets in, it might be that there’s really only one option left: To eschew the advice of the masters and duplicate the code.

Posted in English, Extreme Programming, Java, Software Development | 5 Comments

Five Unit Tests Tips #3: Parametrized test methods

The following is a trick I don’t use very often, but when I do need it, it comes in very handy. It’s a trick that many developers aren’t aware of, even though it’s been possible to do with JUnit at least since version 3.

Sometimes you want to have a lot of tests that are almost the same, but that contain different arguments. For example, for a yahtzee calculator, you might want to have the following tests:

checkRollScoredAsCategoryGives(1, 2, 3, 4, 5, "straight", 15);
checkRollScoredAsCategoryGives(1, 2, 3, 4, 4, "straight", 0);
checkRollScoredAsCategoryGives(3, 3, 3, 4, 4, "full house", 17);
checkRollScoredAsCategoryGives(1, 2, 3, 4, 4, "full house", 0);
checkRollScoredAsCategoryGives(4, 4, 4, 4, 4, "full house", 0);

This is possible with JUnit, but a little trick. You have to construct a test suite manually and add special subclasses of TestCase to it:

 
 
public static Test suite() {
    TestSuite suite = new TestSuite(
          YahtzeeScoreTest.class.getName());
    suite.addTest(checkRollScoredAsCategoryGives(
            1, 2, 3, 4, 5, "small straight", 15));
    suite.addTest(checkRollScoredAsCategoryGives(
            1, 2, 3, 4, 4, "small straight", 0));
    suite.addTest(checkRollScoredAsCategoryGives(
            3, 3, 3, 4, 4, "full house", 17));
    suite.addTest(checkRollScoredAsCategoryGives(
            1, 2, 3, 4, 4, "full house", 0));
    suite.addTest(checkRollScoredAsCategoryGives(
            4, 4, 4, 4, 4, "full house", 0));
    return suite;
}
 
private static Test checkRollScoredAsCategoryGives(
        int die1, int die2, int die3, int die4, int die5,
        final String category, final int expectedResult) {
    final int[] dice = new int[] { die1, die2, die3, die4, die5 };
    return new TestCase("Rolling for " + category) {
        @Override
        public void runTest() throws Throwable {
            YahtzeeScoreboard board = new YahtzeeScoreboard();
            board.scoreRoll(category, dice);
            assertEquals(expectedResult, board.getTotalScore());
        }
    };
}

The code creates an anonymous inner subclass of TestCase that instead of calling all methods annotated with @Test just executes our specific test. These tests are collected in a normal JUnit TestSuite.

The test is plain JUnit and will run in Maven or your favorite IDE, just as any other tests. The fact that the suite is named after the test class will let Eclipse know where to go when you double click on the test from the test runner.

This trick can be very useful for tests of logic that calculates a results or validates input.

Posted in English, Java, Software Development | 12 Comments

Low hanging fruit for presenters

If you ever talk to a group of people, you know that the art of presentation is one that requires a lifetime to master. But there are some dirt simple things you can do that will have a positive impact on your presentations. Here is my list of low hanging fruit for presenters:

  • If you’re using a computer, use a presentation remote. This is a cheap and easy way to make your presentation style look a little more professional.
  • If you’re using visuals, try and place yourself to the left of the visuals from the point of view of the audience. In the western culture, people scan scenes from left to right. By standing to the left, they will look at you first.
  • If your using visuals, place a laptop (or a monitor) between you and the audience with your slides on them. Turning to look at the slides over your shoulder seems uncertain, looking down at the monitor seems thoughtful.
  • Before you start speaking, take a few good breaths. Don’t rush. And whatever you say first, “ummm…” and “yes….” should not be it.
  • When you’re done speaking say “thank you for your attention”. This will trigger the primate clapping response. An uncertain ending leaves the audience wondering when they should applaud.
  • Find the friendly faces. Every audience contains those few people that smile when you look at them. Use them whenever you’re uncertain an need a kick of positive energy.

There are many hard and time consuming skills required to give good presentations. The list above is full of no brainers. These things you can do with no practice and no preparations.

Posted in English | 5 Comments

Architecture as tidying up

Unstructured picture
Unstructured picture

I recently started on a new project. Looking over the code base, I saw the familiar structure of many projects: Definitions of classes goes here, persistence logic goes over there, interfaces to the persistence logic goes this other place, code for transforming from one structure to another in yet another place and so on. This is common, neat, and unfortunate.

As an exercise to understand the architecture of this system, I decided to add some new functionality: Displaying some data to the user. I haven’t worked this task oriented with this sort of system before, and so I hadn’t noticed just how extremely clumsy the common structure of these projects is to work with. In order to create the functionality, I had to navigate to around 10 different directories. In each directory, I had to work with one single file, and ignore the tens of files around it with similar names.

Tidied picture
Tidied picture

While watching a few videos from the TED-conference, it finally struck me: We often think that the job of software architecture is to tidy things up, so that things with the same attributes are sorted into neat piles. Too often, the attribute that we chose as the basis for our organization is an incidental, inconsequential one.

(more…)

Posted in English, Java, Software Development | 7 Comments