Tuesday, July 8, 2014

Pros and cons of Unit Tests

I did a code review for a co-worker today.
I suggested that he refactor his code to make unit tests possible and then to add unit tests.

He argued against adding the tests. Here are some of his arguments against unit testing along with my responses.

Against Unit Testing Responses.
You're making the code more complex!

You want me to add factories and abstract classes and so on, just so things are more testable. You're asking me to rewrite a lot.

I don't want to re-write code that already works.
This is true.
Some things got more complex.

But see, writing code to become more testable, has the side effect of making the code more modular.

And making code more modular is good. 
You have to learn a lot to get going.

New frameworks, new tools, new concepts. All of these new things make things more confusing and complex.

This might be a fad that we forget about in a month or two. 
Learning is part of the job of being a programmer. It's one of my favorite parts.

Maybe the framework and tools we use for testing will change over time.

But you can't argue that the concepts are a waste to learn about.

Even if you don't want to use the concepts, it's cool to understand and learn. No?
Writing test code is a pain in the neck.

You are doubling my work load with no increase in production!
I disagree.
Writing test code is fun.
I've already tested it.

Trust me, it works. Why write a test?
Writing unit tests allow someone else (even a dumb machine) to test your code.

Otherwise, if I have to change your code, I'll have to stop by your desk and you'll have to tell me about it. Isn't that a waste of your time?

Sunday, July 6, 2014

Android Testing

For the last few days, I have been adding more tests to my Android projects. During this time, I have come to the conclusion that:

Unit tests are impossible in Android.

Maybe I should qualify that statement a little bit. Here's something that is more accurate:

For me, setting up unit tests in Android is so difficult, and running them is so slow, and learning and integrating external tools/code is so arduous, that it doesn't seem worth it to hack together a true set of unit tests.

In the mean time, here are the things I am doing in regards to Android testing.

1. Sticking with the emulator
I am running all of my tests and the app in the emulator or an attached physical device. The downside of this is that things are slow. I briefly tried to use Robotium, a highly regarded test framework that helps run your tests outside of the emulator. Maybe I will try again in the future. For now, I am wary of investing more time to hunt down external tools to get this to work.

2. Using the simplest test case that is needed.
I can't seem to keep track of all the test case classes. Here are the ones I use in order of increasing complexity and dependency on Android APIs:

TestCase > AndroidTestCase > ActivityUnitTestCase > ActivityInstrumentationTestCase.

For any given class that I'd like to test, I try to use the simplest test case that works. It seems like this would be the best way to isolate issues and keep things running as fast as possible.

3. Refactoring my code
In the hope of making each class as simple as possible, I have been refactoring my code. In the least, I have been adding comments to say what dependencies a given class has which tells me which test case class is required.

4. Waiting.
I started developing an Android App just to see how things work. It's a learning adventure, not a business one. This is why I can afford to simply wait for the product to improve.

In the future, I may upgrade my machine, which will speed things up. Google may add more libraries, update Android Studio or modify the testing framework to make things easier.