JavaScript Design Patterns - Behavioral - Chain of Responsibility
The chain of responsibility pattern allows passing requests along a chain of objects that have a chance to handle the request.
Upon receiving a request, each handler decides whether to process it or pass it on to the next handler in the chain.
In the example below, we are chaining the class discount to handle the request for how much the discount in a shopping cart is.
class ShoppingCart {
constructor() {
this.products = [];
}
addProduct(p) {
this.products.push(p);
}
}
class Discount {
calc(products) {
let ndiscount = new NumberDiscount();
let pdiscount = new PriceDiscount();
let none = new NoneDiscount();
ndiscount.setNext(pdiscount);
pdiscount.setNext(none);
return ndiscount.exec(products);
}
}
class NumberDiscount {
constructor() {
this.next = null;
}
setNext(fn) {
this.next = fn;
}
exec(products) {
let result = 0;
if (products.length > 3) result = 0.05;
return result + this.next.exec(products);
}
}
class PriceDiscount {
constructor() {
this.next = null;
}
setNext(fn) {
this.next = fn;
}
exec(products) {
let result = 0;
let total = products.reduce((a, b) => (a + b), 0);
if (total >= 500) result = 0.1;
return result + this.next.exec(products);
}
}
class NoneDiscount {
exec() {
return 0;
}
}
Use this pattern when more than one object can handle a request and that information is known in runtime.
A complete example is here 👉 https://stackblitz.com/edit/vitejs-vite-ekmecn?file=main.js
I hope you found it helpful. Thanks for reading. 🙏
Let’s get connected! You can find me on:
Hashnode: https://nhannguyen.hashnode.dev/
X (formerly Twitter): https://twitter.com/nhannguyendevjs/
Buy Me a Coffee: https://www.buymeacoffee.com/nhannguyendevjs