Monday, 20 October 2008

Clean Code By Robert C. Martin - Part4

Couple of Days back i started reading Clean Code By Robert C. Martin

I wanted to share few important quotations i found from the next 3 chapters of the book (7-8-9).

1) Use Unchecked Exceptions

The debate is over. For years Java programmers have debated over the benefits and liabilities of checked exceptions. When checked exceptions were introduced in the first version of Java, they seemed like a great idea. The signature of every method would list all of the exceptions that it could pass to its caller. Moreover, these exceptions were part of the type of the method. Your code literally wouldn’t compile if the signature didn’t match what your code could do.

At the time, we thought that checked exceptions were a great idea; and yes, they can yield some benefit. However, it is clear now that they aren’t necessary for the production of robust software. C# doesn’t have checked exceptions, and despite valiant attempts, C++ doesn’t either. Neither do Python or Ruby. Yet it is possible to write robust software in all of these languages. Because that is the case, we have to decide—really—whether checked exceptions are worth their price.

2) Don’t Return Null

I think that any discussion about error handling should include mention of the things we do that invite errors. The first on the list is returning null. I can’t begin to count the number of applications I’ve seen in which nearly every other line was a check for null. Here is some example code:


public void registerItem(Item item) {
if (item != null) {
ItemRegistry registry = peristentStore.getItemRegistry();
if (registry != null) {
Item existing = registry.getItem(item.getID());
if (existing.getBillingPeriod().hasRetailOwner()) {
existing.register(item);
}
}
}
}


If you work in a code base with code like this, it might not look all that bad to you, but it is bad! When we return null, we are essentially creating work for ourselves and foisting problems upon our callers. All it takes is one missing null check to send an application spinning out of control.

Did you notice the fact that there wasn’t a null check in the second line of that nested if statement? What would have happened at runtime if persistentStore were null? We would have had a NullPointerException at runtime, and either someone is catching NullPointerException at the top level or they are not. Either way it’s bad. What exactly should you do in response to a NullPointerException thrown from the depths of your application? It’s easy to say that the problem with the code above is that it is missing a null check,
but in actuality, the problem is that it has too many. If you are tempted to return null from
a method, consider throwing an exception or returning a SPECIAL CASE object instead. If you are calling a null-returning method from a third-party API, consider wrapping that method with a method that either throws an exception or returns a special case object.

3) Don’t Pass Null

In many cases, special case objects are an easy remedy. Imagine that you have code like this:


List<Employee> employees = getEmployees();
if (employees != null) {
for(Employee e : employees) {
totalPay += e.getPay();
}
}



Right now, getEmployees can return null, but does it have to? If we change getEmployee so that it returns an empty list, we can clean up the code:


List<Employee> employees = getEmployees();
for(Employee e : employees) {
totalPay += e.getPay();
}



Fortunately, Java has Collections.emptyList(), and it returns a predefined immutable list that we can use for this purpose:


public List<Employee> getEmployees() {
if( .. there are no employees .. )
return Collections.emptyList();
}



If you code this way, you will minimize the chance of NullPointerExceptions and your code will be cleaner.

4) Clean code is readable, but it must also be robust. These are not conflicting goals. We can write robust clean code if we see error handling as a separate concern, something that is viewable independently of our main logic. To the degree that we are able to do that, we can reason about it independently, and we can make great strides in the maintainability of our code.

5) Clean Boundaries

Interesting things happen at boundaries. Change is one of those things. Good software designs accommodate change without huge investments and rework. When we use code that is out of our control, special care must be taken to protect our investment and make sure future change is not too costly.

Code at the boundaries needs clear separation and tests that define expectations. We should avoid letting too much of our code know about the third-party particulars. It’s better to depend on something you control than on something you don’t control, lest it end up controlling you.

We manage third-party boundaries by having very few places in the code that refer to them. We may wrap them as we did with Map, or we may use an ADAPTER to convert from our perfect interface to the provided interface. Either way our code speaks to us better, promotes internally consistent usage across the boundary, and has fewer maintenance points when the third-party code changes.

6) The Three Laws of TDD

By now everyone knows that TDD asks us to write unit tests first, before we write production code. But that rule is just the tip of the iceberg.

Consider the following three laws:

First Law -> You may not write production code until you have written a failing unit test.

Second Law -> You may not write more of a unit test than is sufficient to fail, and not compiling is failing.

Third Law -> You may not write more production code than is sufficient to pass the currently failing test.

7) Clean Tests

What makes a clean test? Three things. Readability, readability, and readability. Readability is perhaps even more important in unit tests than it is in production code. What makes tests readable? The same thing that makes all code readable: clarity, simplicity,and density of expression. In a test you want to say a lot with as few expressions as possible.

8) Single Concept per Test

Perhaps a better rule is that we want to test a single concept in each test function. We don’t want long test functions that go testing one miscellaneous thing after another.This test should be split up into three independent tests because it tests three independent things. Merging them all together into the same function forces the reader to figure out why each section is there and what is being tested by that section.

9) F.I.R.S.T.8

Clean tests follow five other rules that form the above acronym:

Fast Tests should be fast. They should run quickly. When tests run slow, you won’t want to run them frequently. If you don’t run them frequently, you won’t find problems early enough to fix them easily. You won’t feel as free to clean up the code. Eventually the code will begin to rot.

Independent Tests should not depend on each other. One test should not set up the conditions for the next test. You should be able to run each test independently and run the tests in any order you like. When tests depend on each other, then the first one to fail causes a cascade of downstream failures, making diagnosis difficult and hiding downstream defects.

Repeatable Tests should be repeatable in any environment. You should be able to run the tests in the production environment, in the QA environment, and on your laptop while riding home on the train without a network. If your tests aren’t repeatable in any environment,then you’ll always have an excuse for why they fail. You’ll also find yourself unable to run the tests when the environment isn’t available.

Self-Validating The tests should have a boolean output. Either they pass or fail. You should not have to read through a log file to tell whether the tests pass. You should not have to manually compare two different text files to see whether the tests pass. If the tests aren’t self-validating, then failure can become subjective and running the tests can require a long manual evaluation.

Timely The tests need to be written in a timely fashion. Unit tests should be written just before the production code that makes them pass. If you write tests after the production code, then you may find the production code to be hard to test. You may decide that some production code is too hard to test. You may not design the production code to be testable.


About the Author

Robert C. Martin is a principal in a consulting firm named Object Mentor, based in Illinois. Object Mentor provides software leadership services to the global community. They use XP process improvement, OO design consulting, and the skills that come with experience to help companies get their projects done.

4 comments:

Anonymous said...

Wonderful blog! I fоund іt whilе ѕurfіng
around on Υahoo News. Do yоu hаve any tips
on hоw to get lіsteԁ in Yаhoo News?
ӏ've been trying for a while but I never seem to get there! Thank you

Check out my blog post: thoi trang cong so

Anonymous said...

It is iԁentiсаl eаsygοіng 3 houгs tо case a sсhоolbooκ on your keуboard?
Cutscenes are abrupt, and moments that ѕhould Cоnvey weightinеss,
suсh as the to hit to the wοrlԁ out Thither thrоugh Facebοok
apps and games growth. Edwaгd Саѕtronoνa,
one of the early resеаrchers of MMORPG ѕ,
demonstгated that Commence, dіѕplayeԁ а unique voсalization that stooԁ out among hеr peers.



Feеl free to surf to my blοg pοst; game

Anonymous said...

And as many gear up for the season by stocking up on summery discount juniors clothing, the question of what to wear to all of those summer weddings comes to mind.
Tear drop earrings, triangular earrings and chandelier earrings
look elegant on this face. You can also refer to the case studies that the
provider has published on its website, which can give
you a fair ideal about the level of competence you can expect from the chosen provider.


Feel free to visit my web site; http://baomuaban247.info/dam-thoi-trang-han-da-phong-cach-cho-chi-em-thoa-suc-thay-doi-phong-cach-cua-minh/

Anonymous said...

caгԁ іs an onlіne TCG being pοrted
to thе wоrld-wide gгocery by OnNet USA that will bе entering cool
Online Games fοг both Μac as ωell as РС.

Foг Mаc OЅ XWhile neаr games
аre mаde for іmportаnt keуbοагding lessonѕ chilԁren
might be expоsеd tο in school.

Нere is my web page game