Entry-6: [Design Patterns] - Chain of Responsibility Pattern
Tags: designpatterns, codequality, techcommunity, softwaredevelopment
Published: 2023-05-02 17:12:52

The chain of responsibility pattern is one of those essentials which can solve the headaches in building an authentication system in react.(or similar)

it’s a **[Behavioral design pattern](https://www.notion.so/S-in-SOLID-c043f159b92f4426a8dd3aaed51c769b)** which encapsulates the logic for a request, passing on that request along each handler or item till it’s ignored or handled as intended.

**So how is this applied in React.**

Say we would like to create an authentication system in react which checks

- If a user is an admin or regular
- checks if a users subscription has expired
- Redirects or shows the appropriate selection.

We can make use of an if/else statement or violate the single responsibility principle but as more requirements arise that logic becomes messy. *plus…* we can move handlers around to handle requests before the next eg. *check subscription before user type*, remove if needed with minimal effort. ie, **Reduced coupling!**

**Implementation**

- create an interface and contract for handling requests

```tsx

interface IHandler {
  setNext(handler: Handler): void; // Can be named differently + (optional) - it passes the request to the next handler.
  handleRequest(request: any): void;
}

Implement Base handler class which is common to all 
```

- Implement base handler which implements logic common to all classes which would use the CoR pattern

```tsx
abstract class AbstractHandler implements IGenericResponsibility {
  private _nextHandler: IGenericResponsibility | null = null;

  public addNextHandler(handler: IGenericResponsibility): IGenericResponsibility {
    this._nextHandler = handler;
    return handler;
  }

  public Handle(args: any): any { // Any can be replaced with your type as needed
    if (this._nextHandler !== null) {
      return this._nextHandler.Handle(args);
    } else {
      return null;
    }
  }
}
```

- create a class which makes use of the abstract class above

```tsx
// base class to handle the common request

class checkAdmin extends AbstractHandler {
  public Handle(args: any): any {
    // Handle the request here, or pass it to the next handler
    // if this handler cannot handle it.
    if (/* condition to handle the request */) {
      return /* Result from handling the request */;
    } else {
      return super.Handle(args); // Pass the request to the next handler
    }
  }
}
// we do the same above for all handlers extending the abstract or base handler.

class checkSubscription extends AbstractHandler {
  public Handle(args: any): any {
    // Handle the request here, or pass it to the next handler
    // if this handler cannot handle it.
    if (/* condition to handle the request */) {
      return /* Result from handling the request */;
    } else {
      return super.Handle(args); // Pass the request to the next handler
    }
  }
}
```

- initialize class which makes use of the concrete handler.

```tsx
const checkAdmin = new checkAdmin();
const checkSubscription = new checkSubscription();

checkSubscription.addNextHandler(checkAdmin); //if we have more handlers we keep stacking.
//Then we trigger the handler by calling the method at which we would like to start from.
concreteHandler.handle(request):
```

- Create hook which makes use of the handler

```tsx
import axios (or preferred) from "axios" or "preferred"

const useCOResponsibility = async ()=>{
const checkAdmin = new checkAdmin();
const checkSubscription = new checkSubscription();

checkSubscription.addNextHandler(checkAdmin); //if we have more handlers we keep stacking.
//Then we trigger the handler by calling the method at which we would like to start from.
const result = concreteHandler.handle(request):

	if(result === "condition")
	{
		//perform condition.
	}
}
```

Making use of a hook should not hinder us as well, as we can also make use of the concrete handler directly within our component ie.

```tsx

const FuntionalComponent = ()=>{

const checkAdmin = new checkAdmin();
const checkSubscription = new checkSubscription();

checkSubscription.addNextHandler(checkAdmin); //if we have more handlers we keep stacking.
//Then we trigger the handler by calling the method at which we would like to start from.
const result = concreteHandler.handle(request):

useEffect (()=>{
	if(result === "condition")
	{
		//perform condition.
	}
},[result]) // or a similar logic to handle a result

return <JSX/>

}

}

```

That’s it.

At the moment, the CoR is one of my favorite design patterns compared to others, such as the strategy pattern. This is because the flow of my logic moves in a sequential and logical manner with the CoR pattern, and it allows me to call one item before the other, switch out places, and apply the single responsibility and open/closed principles with less complexity. These factors result in clear and concise functionality in my code.

What do you think/which is your pattern and why do you make use of it.? Feel free to send your response as a message or comment below.

### **Resources**

- Wikipedia - **[Chain-of-responsibility pattern](https://en.wikipedia.org/wiki/Chain-of-responsibility_pattern)**
- [https://refactoring.guru/design-patterns/chain-of-responsibility](https://refactoring.guru/design-patterns/chain-of-responsibility)
- [https://www.javatpoint.com/behavioral-design-patterns](https://www.javatpoint.com/behavioral-design-patterns)

**External Links**

- **Twitter**: [@benny_wayn](https://twitter.com/etieno_u)
- **LinkedIn**: [Ibenge-uforo](https://www.linkedin.com/in/ibenge-uforo/)
- **Ongoing** **Research**: [Social Survey](https://docs.google.com/forms/d/e/1FAIpQLScKBo1VQvEVpvxKbOamhWq02uQU8HlgUPq576F-LD3yTljkwg/viewform)