Learning Single Responsibility Principle by Example
Tags: javascript, solid, programming
Published: 2021-07-16 13:17:11

Welcome to this first article in which I will show the importance of applying the [**Single Responsibility Principle**](https://en.wikipedia.org/wiki/Single-responsibility_principle) when implementing the code of our application.

There are many **advantages** to applying this principle: code comprehension, component reusability, increased development speed, ease of testability, etc. All of them affect the development team in the way they work and, indirectly, affect the end-user in the way they receive new functionalities.


**What Single Responsibility means**

The [**Single Responsibility Principle**](https://en.wikipedia.org/wiki/Single-responsibility_principle)  is framed within the set of [**SOLID principles**](https://en.wikipedia.org/wiki/SOLID), a set of rules to guide our code in what it's called **Clean Code**. In this case, each letter represents a different principle:

* S for [**Single Responsibility Principle**](https://en.wikipedia.org/wiki/Single-responsibility_principle),
* O for [**Open/Closed Principle**](https://en.wikipedia.org/wiki/Open%E2%80%93closed_principle),
* L for [**Liskov Substitution Principle**](https://en.wikipedia.org/wiki/Liskov_substitution_principle),
* I for [**Interface Segregation Principle**](https://en.wikipedia.org/wiki/Interface_segregation_principle),
* D for [**Dependency Inversion Principle**](https://en.wikipedia.org/wiki/Dependency_inversion_principle)

Different programmers tried to describe this principle in the past, the one by [**Robert C. Martin**](https://en.wikipedia.org/wiki/Robert_C._Martin) is the standard as **de facto**:

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
_A module should have one, and only one, reason to change._
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

The statement is quite simple, although, according to the author, it is the principle least understood. At first sight, the sentence is clear and there seems to be nothing unusual. However, the `module` word could have **different meanings** for each person and lead to confusion.

We understand `module` as a set of files or components that involves a *use case* or functionality in our application just for *one actor*. I have to say that this definition is no as specific as I would like to be because it relies on the programmer's experience to decide on what implies an actor and a use case.

I don't have any other better definition; however, I try to solve it following this principle in functions and objects. At the end of this article, you will be able to change your way of coding based on what I'll show you.

**Coding for learning**

Most of the time, seeing an example is easier to understand than reading a load of lines in an article. This example shows how the code is changed to follow what the [**Single Responsibility Principle**](https://en.wikipedia.org/wiki/Single-responsibility_principle) says. We will start with a simple example of code that works fine and then refactor it without affecting the functionality.

In this case, I want to show the sequence of **Natural numbers** (starting from 0 to Infinity) waiting **one second** between each printing. It seems so simple to code. The most complex task here is to wait for 1 second each time a new number appears to the user. We will use the `setInterval` method to accomplish that.

```JavaScript
var number = 0;

var id = setInterval(function() {
  console.log(number); 
  number++;
}, 1000);
```

As you can see, this is very simple. If you run this code on your browser or your Node.js console, you will see one line per number.

However, this code is doing several things at the same time:
* Sets 1000 ms for each execution,
* Implements the code to be executed in each execution

In resume, **too many things** for this little example. If you are doing pair programming and your mate doesn't know the use case, it will be difficult for her to understand what this code intends.


**Refactoring the code**

Now, we need to separate **responsibilities**. For the first of the things I've listed before, we define a `Timer` entity that will be **in charge of** executing some functionality every second of a frequency passed. The code for the `Timer` entity could be like the following:

```JavaScript
function Timer(frequency) {
  
  let intervalId = null;
  
  return {
    start: function(job) {
      intervalId = setInterval(job, frequency * 1000);
    },
    
    stop: function() {
      if(null !== intervalId) {
        clearInterval(intervalId);
      }
    }
  };
}
```

As you can see, I'm defining a way to `start` the timer and another to `stop` it. A timer is just a **tool** for our system with no other concern than run tasks with a frequency.

For the second thing I've listed, we define a `Job` entity that will be **in charge of** executing a task. In our case, we have to define one job for printing the Natural numbers sequence:

```JavaScript
function PrintNaturalNumbersJob() {
  let number = 0;
  
  return {
    next: function() {
      console.log(number);
      number++;
    }
  };
}
```
Simple code where we are taking care of the number shown before to print the next one. `Next` method prints the current number and increments the same variable for the next time.

As we are implementing an application, we also need an `App` entity defined in our code. It will combine both previous entities in the following code:

```JavaScript
function App() {
  let frequency = 1; // In seconds
  
  let timer = new Timer(frequency);
  let job = new PrintNaturalNumbersJob();

  timer.start(job.next);
}
```

This code is easy to read, so to maintain. Your mate who needs to validate that your code is compliant with the acceptance criteria of the use case will identify all that she needs to verify. The frequency of execution sets to 1 second in the first line of the app, and the task to be executed will print the sequence of Natural numbers. Now, your mate can reach the code of each entity and check if it is doing the right things, or, in a better way, **its responsibility**.

**Wrapping up**

This article shows **how to improve our code and its maintainability** by applying the [**Single Responsibility Principle**](https://en.wikipedia.org/wiki/Single-responsibility_principle).

This is something complex to apply at the beginning if you are not used to it but makes you grow up on how to design the components of your app. Once you have some experience you can apply this principle to your app modules.

What do you think about the exercise made in this article?
Hope this can be useful to you or just have fun reading it.