Unit test – call the agel out of the stone

Angel

Angel, please come out of the stone

“I saw the angel in the marble and carved until I set him free” – Michelangelo

After the previous post when I managed to make Spring context wired for Unit test to run, now there’s more thing into it. Well, I gave my Test class the ability to do IOC (Inversion of Control), and from now they can call service beans, access databases, and so on… It seems the remaining should be easy, since the hardest part has been completed.

Well, things don’t easily go as we expect, in lots of occasions.

I actually made a running code, but when I try writing my first unit tests for my current working web-application, things turn bad. It turns out that I can’t write much meaningful non-trivial test, without making test-running-time tremendous slow. Why? It’s because:

1. Most of my code logic lies in the service. AND the service (in this project) OFTEN (if not always) works with Database. And when I says Database, it means the test is not the unit test anymore. It’s an Integration Test.

2. There’s some logic in my project which doesn’t relate to database. But I feels pretty confident about them – they are mostly simple. According to Pareto’s 80/20 rule, I don’t want to write tests that doesn’t enhance maintenance ability.

Those may be (some of) the reasons that my seniors don’t encourage me to write unit test. Unit tests are meant to be fast. If it’s not fast, there’s no reason to run it frequently, to help refactoring or development.

Another problem I meet is to set up the Database to a known state before running the test. Only then the test results will have some meanings.

So… are the efforts all useless. Absolutely no. The main problem here is that I need to stop regression bugs, by regularly running some kind of test. Whatever it is, but let me find bugs soon, and stop the system broken by ill-refactoring.

“And I have found the solution. The way to call the angel out of the stone”. If I can put up an in-memory database instead of Postgres, the running-time will be fast. I can also prepare the environment by database script or bootstrap code.

DBUnit seems to be a fair choice for a solution.