Newsletter sign-up
View all newsletters

Enterprise Java Newsletter
Stay up to date on the latest tutorials and Java community news posted on JavaWorld

JavaWorld Daily Brew

Thinking Inside a Bigger Box

Welcome to Johannes Brodwall's blog. I use this space to work on articles mostly about software development, with a focus on Java, SOA, and Agile software development. Many of the articles you will find here are not much more than drafts, and I certainly appreciate input on how to make them better.

If you wonder about the title of this blog, Thinking Outside the Box may answer your questions.

I work as the lead software architect of BBS, the company that handles interbank services in Norway. In my copious free time, I develop software and consult companies in development practices and architecture. For more about the services I can offer, please see my resume.


Unit testing tricks: Look ma, no setters!

 

Here’s a neat trick if you want set an object in a specific state in a unit test, but you don’t want to violate encapsulation:

@Test
public void withdrawShouldReduceBalance() {
Account account = new Account() {{
super.balance = 100;
}};
account.withdraw(10);
assertEquals(90, account.getBalance());
}
 
@Test(expected=IllegalStateException.class)
public void overdraftShouldThrow() {
Account account = new Account() {{
super.balance = 5;
}};
account.withdraw(10);
}

This seemingly magic code lets me have a protected (but sadly not private) field Account#balance. I can set this field in each individual test method.

It looks very magic, so it deserves a brief explanation:

  1. The first set of curlies create an anonymous subclass of Account. That is: new Account() {}.
  2. The second set of curlies creates an initializer block, that is: a block of code that is added to the constructor.
  3. So in effect: Each test method creates a subclass of Account and modifies the account field in the constructor. This is why Account#balance must be protected instead of private.

This trick (and it is a trick) lets me set up the object under test to any state I want, without needing a special constructor and without breaking encapsulation by adding a setter. However, I’m required to make the fields I want to initialize protected. Additionally, each test method creates one or more new classes. This could potentially affect performance and/or memory use during compilation and/or running of tests. I’ve only used the trick at a small scale, so I don’t know if I’ll run into these issues in the future.

So, what do you think: How big of a “WTF” is this code?