Why Test Software? Tests Help Communicate Complexity

Why Test Software? Tests Help Communicate Complexity

Last updated:

Software in the large is one of the most complex things humans have created.

Software is complex because it's invisible, because it's not tangible.

You can't "show" 500,000 lines of code to someone and tell them "see here? This is what my program does" the same way you can show a friend a building and say: "This is what my building is like".

There's not much ambiguity in the physical world. You show someone a door (it might even be a somewhat more advanced door or something like that), you can be sure you and they are looking at the same thing. There's no risk of you pointing at a straight edge and them "seeing" a round edge.

Not so with software. The layers of abstraction are so deep that it's much more difficult to share your understanding of a codebase. Things will get misunderstood in the process.

But that's not really where testing comes in. This is not where the real complexity lies, in my opinion.

Perfection is expected from software. Perhaps because you can't negotiate with it (unless you dive into the code in order to hack it) on a physical level.

If you live in a building whose door is too small, you can perhaps hire someone who, with a little work, increase the size of the door with a few hammer strokes or something like that. In other words, the physical world is negotiable with the tools you have.

If you have a piece of software that doesn't do what you want, you're basically screwed. You can't quickly adjust it the same way you can a door that's too small (using a simple hammer)

However, since business objectives are always changing, users always want other features from software. This isn't bad at all, mind you — it's something we accept when we become software developers.

The natural consequence of this is that software needs to be constantly changed and updated. Not just adding more features, but combining existing features into new ones, removing now useless features, adding newer levels of abstraction and so on. This is what kills bad software in the long run. Complexity becomes unmanageable and nobody knows what side is up anymore.

The fact is that we can't avoid changing software, because we live in a changing world. Software supports all other industries in the world. Every sector in an economy needs software to make their process more effective, costs lower and so on.

We can't not change software. So what do we do? We embrace change. And take steps to enhance the process.

The solution is testing. A lot of test cases. Unit tests, functional tests, integration tests, user interface tests, you name it. Yes it's a lot of work, but the alternative is code that does not survive more than a couple of years of changing requirements.

Having an all-around testing framework under our software is the only way we can proceed to change it to adapt to new expectations (remember, we just can't avoid it) and be sure that the system as a whole still works.

Removing unused code is just as important as adding more features if you're to keep your project to a manageable size. Without tests, you'll just never perform the necessary structural changes that newer requirements make unavoidable. You just won't do anything that may cause your existing system to break down. And you'll have no idea what sort of functionality may break when you change your code unless you can run tests to verify that.

Having a large number of test cases that you can run automatically after each change is the only way software can evolve with time and not turn into a frankenstein.

Dialogue & Discussion