The fundamental notion is that a given object should assume as little as possible about the structure or properties of anything else (including its subcomponents).That's all well and good, but I quite like the Law of Demeter because it's the canary (warning device) in my coal mine (codebase).
I was recently looking over some code with Mike Ward, Shane Harvie, Muness Alrubaie, Martin Fowler, Dan Manges, and David Vollbracht. The code in question had around a hundred lines of
def_delegator :object, method_name, new_method_name. No one in the room thought that the 100+ lines of delegation were a good thing, but we all had opinions on how to deal with the ugly code.
Despite the various opinions on solutions, one thing was clear: The Law of Demeter exposed other issues within the codebase. For example, the object in question was taking on far too much responsibility. It had become the DoAnything object of the system. Additionally, methods such as
diamond.clarity=were being delegated from
ring.diamond_clarity=method. These methods were required as the attributes of a diamond were changed. However, a possibly better solution would be a method such as
ring.replace_diamondthat set an entirely new diamond. With the replace_diamond method in place the ring no longer needed to expose the setters of the diamond.
An additional note that came from this conversation: If you are a mockist you will often prefer to follow the Law of Demeter because it makes mocking much easier. However, classicists don't seem to mind as much since they can use train-wreck syntax for state based tests without any pain. Being a mockist or classicist seems to greatly influence a person's opinion on whether or not to follow the Law of Demeter.