I have two projects at work -- one is new, and I'm using Spring, and unit tests and life is good. But one is old -- quite old. There is code from five years ago, which is positively ancient for a J2EE application! This app is just a Big Ball of Duct Tape.
Some of you are familiar with the Big Ball of Mud concept. You know, when someone just pounds more and more stuff into an application and it turns out so spaghetti-like it's unbelievably difficult to work, to change, to fix, etc. My Big Ball of Duct Tape is like that, only that there were at least five development teams that have worked on this, each with different abilities. Some are still at the company, and have confided in me that this was their first J2EE application.
I think this app started out pretty good, but when they needed to make changes, like bug fixes or added functionality, they didn't gracefully put it in. Instead they stuck it on with duct tape. And, when they needed to fix those bugs, they used more duct tape. And when more functionality was needed, they added more duct tape. When I got it, the app is so horrid, so temperamental, that a small change can have disastrous results. And I can show you an 10,000 line Struts ``Action`` class to prove it.
Needless to say there are plenty of odd things that happen in this app, it gets saved to a database. Every hour another app has a batch job that looks at my database, finds what the user turned off and turn it off in their app. Janky? Very. And prone to breakage.
It seems that if my app doesn't save it right, the other app can't find the changes. So my app has it turned off and the other app has it on. That messes with my users, who can look at both things. And some people only look at the other app. Yeah, it's a mess.
I was assured that this only happened once in a while, and they sent me an email saying what I had to do to fix the database. That email described the exact state that the database needed to be in for App #2 to find the info and the bad state that the DB was in when the update didn't happen. It sounded like someone researched the problem thoroughly, but I still wasn't sure why no one fixed it. I guess some duct tape was enough.
Late last week, I got the call that it had happened. I was in a hurry because I had a training class starting in a few minutes, so I quickly made the update and went to class. I left a message with the user that called me and said to let me know right away if there were problems.
On Monday, I got a call from another user that said it was still not fixed. And then he said, "How come our software never works?"
Well, now we are in a different situation! I dropped what I was doing and went full board into the issue. I re-read the email that described how to fix this, and did it right this time. I called the user back and said that, at the next sync (which happens every hour) it should be fixed and to call me back if should. And then I told him I was going to look and the issue and solve it once and for all.
I started up my dev environment, and could easily replicate the problem. Good -- Step 1 down.
So I started unraveling the duct tape. Slowly and surely I unwrapped it, carefully making sure that nothing fell off. I started removing unused variables (which were legion) and got to the offending section. That section has a nice, long comment about the fact that the present code wasn't a good fix and it needed to be fixed soon. That comment was dated in 2003.
But as I looked closely at it, I wasn't sure that section was ever actually called. A log message into that section confirmed it. I looked up above and saw very, very similar code. I put a log message in that section -- bingo!
I took the nicely commented code, warning and all, and put it in it's own method, put a flag on it so I knew which section called it, and made both parts of the code call that method instead of having the same logic in twice.
As I started poking at it, I figured out what it was. The logic should have been to make a copy of the object, and then make a state change. The actual code changed the state first, and then made a copy! So, we were never saving the right data to the database after all.
Did I mean never? Yes, I did -- with "never" meaning ever since I inherited the code. And, I guess, ever since the developer before me inherited the code, since they are the ones that warned me that it happens once in a while.
Somewhere in that time, I noted that two hours had passed and I hadn't heard from my user yet. I called him and asked him to check the applications again. "I'll be darned, " he said, "things are working now!"
I still need to test my changes to make sure that nothing bad happens. Such is life when you support an application that is a Big Ball of Duct Tape.