October 29, 2011

Who is my Koala keeper?

This post contains answers to the puzzler presented in my previous post Observer Pattern: Part I - How to mess up your code with it.

All the code presented in the previous post is here:

What was wrong with the code?

There were 3 things wrong with the code:
  1. The WaterPipe is not getting fixed
  2. The Boss is observing the Koalas, but when they are hungry, all he does is complain
  3. Whenever the ZooKeeper feeds a Koala, the Boss is notified twice

Was the Boss supposed to observe the Koala?

Well, we have no way of knowing for sure just by looking at the code. I try to avoid puzzles with no clear answer in the future, but there was no going around for this one. When you do not type strictly, you just miss the information in the code if something goes wrong.

The initial though you probably had is that it probably is a mistake to add the Boss as the observer for the Koala, because he does not have the Koala-feeding code in his update method. But you cannot know for sure.

It is also possible (though not probable) that, for example, the Boss was supposed to feed the Koalas while the ZooKeeper is on vacation, but the implementation was never completed. We would need to search through the code and try to find if ZooKeeper ceases to observe the Koalas at some point. If we find such a code, we must fix the Boss so that he can feed the Koalas. If the ZooKeeper is available all the time, we can assume that the Boss should probably not be observing the Koalas. 

Could something like this really happen? Why would someone code something like this?

Yes, and no. 

The broken pipe was my own addition. As we do not have a complex subject and 10.000-50.000 lines of code here, I needed some distraction for you. I do not think it is a common mistake to totally mix up the observers like that. That type of mistake is possible, but as the pipe-fixing functionality would stop working altogether, it would be caught in the testing quite fast and thus the error would not survive long. 

But what happened with the Boss is real. I have fixed a similar bug. One of the nasty things about this pattern implementation is that the only reference to update method is in the java.util.Observable. The codebase had about 10 different Observers and I had to check through them all while I tried to find out who should observe who. Only after that was clear, was I able to concentrate on trying to find out what is wrong. The update method having and argument of Object array with four unknown Boolean and Integer parameters did not help either. 

Finally I came into conclusion that probably the Boss and the ZooKeeper had originally both been observing the Koala. At some point someone had thought that it is better that the ZooKeeper keeps the Boss informed. And while he remembered to remove the Koala-feeding code from the Boss, he did not remember that the Boss was still added as Observer for Koalas. We were getting quite a lot of extra notifications! 

While the similar situation could have occurred with better implementation of the Observer Pattern, it could not have happened by mistake. If strict types would have been used, the programmer would have gotten a compilation failure for trying to add the Boss as an observer for Koala.

In the next part of this series, I'll show you better ways to implement the Observer Pattern.

No comments:

Post a Comment