Approaching the Finish Line

Frame2 is almost ready to be released as a new version. I may still make some changes, but it’s definitely in Release Candidate stage now. There are only a few things that I may add before testing the heck out of it:

  • Upgrade unit tests to JUnit 4. There are a lot of tests, especially the ones that mock a servlet container, that do a lot of repetitive work in setUp() . JUnit 4 has finally brought the ability to annotate methods to be run before and after all tests in the class with @BeforeClass and @AfterClass, respectively. Individual test setup activities can still be performed by annotating a method with @Before.
  • Fix outstanding bugs. There’s only one right now, and it’s SOAP specific, so I may or may not fix it. It may take me longer to figure out how to reproduce the problem with unit tests than it’s worth.
  • Add outstanding feature requests. Again, there’s only one, but it’s (in my opinion) a biggie - the ability to add parameters to the response when handling an event.
  • Doc updates. The web services doc needs to be written, and I’m sure all of the other doc needs a good examination.

I’ll be testing the latest build with a web application that I’ve been working on for years that I’ve come to think of as an unofficial reference implementation of Frame2. I haven’t decided yet if the web app should become part of the project on Sourceforge or not. We’ll see.

Once the testing is done and I’ve released a new version of Frame2, I plan on working on the Eclipse plugin. The poor plugin has pretty much been ignored for several years now, and it needs some attention.

A Consistent API is a Very Good Thing

I’ve been mucking around in the codebase, cleaning up pieces of the API that annoy me. Some bright person thought that it was a good idea to have a method that returns an Iterator to access a collection. I’ve been cleaning up all of these methods, changing them so that they return an actual collection - occasionally made unmodifiable through the Collections class.

Naturally, this has led to unit test failures. Almost all of the failures have been easy to fix, but once in a while one pops up that makes me scratch my head. Here’s an example:

public void testGetIfEmpty() {
assertTrue(this.errors.isEmpty());
assertNull(this.errors.get(FOO));
assertEquals(0, this.errors.get().length);
assertEquals(0, this.errors.get(FOO).length);
}

In this instance, errors is a class that aggregates individual Error objects. The get(String) method returns an array of Error objects that have the specified key, while get() retrieves all Errors. Pretty simple, right? After my changes, the test fails on the assertNull() statement, which isn’t surprising.

The failing statement read assertNull(this.errors.iterator(FOO)) before I removed the iterator() method, which tells us a bit about how the API was originally coded. The iterator(String) returned null if there were no matching entries. However, as the unit test clearly shows, get(String) returns an empty array when it doesn’t find any matching Errors. Quite the difference, and potentially confusing - the developer has to remember which method may return null.

The API has now been changed to return an empty collection instead of null when no matching errors are found. Now, a user of the API simply has to call the method and loop over the result (zero times if it’s empty) without having to make null checks.

Whoever wrote this unit test obviously knew that one method returned null while the other returned an empty array for the same input, since the test passed. I only wish that person would have looked at those lines and noticed the inconsistency, instead of leaving it for me to find.