Technologist and Maker

I have always admired the cleverness of the name Hollywood Principle. I love its name! The essence of this principle is “don’t call us, we’ll call you”. As you know, this is a response you might hear after auditioning for a role in a Hollywood movie. And this is the same concept for the software Hollywood Principle too. The intent is to take care to structure and implement your dependencies wisely.

At its most basic level, the principle is about reducing the coupling in a software system. It gets back to the well known phrase in software development: loose coupling and high cohesion. You can keep classes loosely coupled by ensuring that you don’t have unnecessary references and you are referencing classes and other subsystems properly. Although the Hollywood Principle does not dictate anything about cohesion, it is an important aspect too. Cohesion is about keeping your classes true to their intent and not allowing their behavior to expand beyond its core purpose. Like high coupling, low cohesion doesn’t tend to cause systems to be unstable or not work properly, but will likely lead to difficulty in maintaining the software.

One of the most popular ways to implement, or obey, the Hollywood principle is to use events or callbacks. A well known pattern that follows the Hollywood principle is the observer pattern. This pattern allows one to observe the state of an object in a well defined and non obtrusive manner. It is typically implemented by injecting a callback object (observer) into the class to be observed (subject). The subject simply raises an event in all observers when its state changes. How the observer reacts to the event is outside the scope or care of the subject.

Dependency Injection (DI), which is a form of Inversion of Control (IoC) is another example of the use of the Hollywood principle. Take for example a shopping cart class that requires a reference to a currency conversion service. Traditionally, the shopping cart class would be designed with a reference to the currency convesion service or use a factory to get a reference to the appropriate service implementation. By contrast, using DI, an external mechamism (e.g. Spring or Spring.net) automatically provides a reference to the required currency conversion service at the time the shopping cart class is instantiated.

The Single Responsibility Principle (SRP) is defined by wikipedia as every object should have a single responsibility, and that all its services should be narrowly aligned with that responsibility.

Although the origins of this concept are someone disputed, most believe it was originally developed by Tom DeMarco in his book Structured Analysis and Systems Specification but was later popularized by Robert Martin in his book Agile Software Development: Principles, Patterns, and Practices. The principle simply states that a given class should have one and only one responsibility. And that the behavior of the class should be narrowly aligned with that single responsibility.

The essence of this concept has to do with the reason to change a class. If a class has more than one responsibility, it may have different reasons to change, each of which are independent of one another. Take for example a class that both imports data from a file and saves the data to a persistent storage mechanism. The single class needs to be modified for any change to the incoming file format as well as any change to the underlying data storage mechanism structure. These changes should not be connected. By modifying the class to adjust the file format, you risk introducing a bug to the file persistence code. In a hurry, without the safety net of automated unit tests (gasp!), developers tend to only test code that is related to a given change.

If your classes follow SRP, you probably can get away with only testing related code (although thorough automated unit tests are always the best course of action). If you violate SRP, you need to be extra cautious when considering the ripple effect from changes to your code. I believe SRP is so fundamental that it can make the difference between a system that is easy to maintain and one that is your worst nightmare to maintain.

Sounds simple right? Well it is, but it is common while designing and refactoring to find SRP violations. But let’s face it. Most software stinks and I have seen countless convoluted designs. Many of these designs (not designed by me of course) had a systemic SRP issue. SRP in one class in your system is not big deal, but SRP in most of your classes is sure recipe for disaster and a system that is very difficult to maintain.

When I have difficulty getting a design to feel right, I try to ask myself whether the classes in that portion of the system are following SRP. Many times, I find the core design issue stems from one or more classes with more than one responsibility.

There are many ways to deal with SRP violations. The most common are:

Delegation – To put behavior in another class and leverage a pattern such as Strategy

Aggregation – To push the behavior out to another class and reference this new class