Friday, 13 November 2009

Porting fidelity

Before Noda Time took off, I had assumed that we would port it by keeping the same class hierarchy (with maybe a few structs or enums instead of classes and constants), changing names to be .NET-idiomatic, and turning getters/setters into properties.

As it happens, we've actually done a fair amount of redesign for the core concepts. For example, in Joda time an Instant has an associated chronology – despite that not making any conceptual sense. It's handy for the implementation, but it's not really "right" from a user's point of view.

My current aim is to create as clean an API as possible without changing the design so much that we need to radically change how it's implemented. To put it starkly: I don't trust myself to fully understand the subtleties of the Joda Time code. Most of the tricky stuff is implemented in the classes which handle calendar systems and time zones, and I want to leave those guts well alone. (We may be using a model closer to JSR-310 for storing/loading time zone information, but we'll see how that pans out.)

To put it another way, I want to be a plastic surgeon, not a heart surgeon. I believe that Joda Time is as strong as an ox, but has a few warts. (Don't get me wrong, it's a lovely library in general – but it would be insane to expect there to be no possible improvements after all this time.) This approach seems to be working for us at the moment, but the proof of the pudding will be in the eating.

Interestingly enough, we're violating the agile "no big upfront design" idea somewhat… we're trying to design a lot of the public-facing concepts at least before implementing anything. I think this is important for something like Noda Time – and it's only possible because we have Joda Time (and JSR-310) to look at and learn from. We're not doing completely blue-sky thinking (i.e. guesswork) – we're just honing the thoughts before making them concrete.

So that's two options (the original idiomatic but high-fidelity warts'n'all approach and the current idiomatic but more liberal one). You can go further in each direction, of course. Some ports appear to be very definitely ".NET with a Java accent" – effectively a mechanical conversion with the very barest nod given to .NET idioms, leaving a fairly unpleasant experience at the end. Others are more "let's take a good idea and rearchitect it from the ground up" – which means you really need to understand the subject matter thoroughly.

Just to make it clear, I do hope that by the end of the project I've learned an awful lot about time. In fact, I've already learned quite a lot. That doesn't mean I would trust myself to try to write Noda Time without borrowing heavily from Joda, however.

All of these approaches have their pros and cons in terms of time-to-useful-implementation, comfort level for developers on the original platform moving over to the new one, elegance for developers who have never used the original version, and freedom to innovate. It's always going to be a tricky path to navigate… but at the moment it feels like we're doing the right thing. Only time will tell for sure.

1 comment: