DEV Community

Cover image for Adapter Pattern with JavaScript
Walther Carrasco
Walther Carrasco

Posted on • Updated on

Adapter Pattern with JavaScript

Hello devs!

Today I challenged myself to write my first post and I wanted to be about the Adapter Design Pattern.

Design patterns are the basis of all good software. A design pattern is a general solution to a reappearing problem.

Now, what is Adapter Pattern? If we bring the problem from the real domestic world, a adapter is used to connect two or more things which can't be connected with their original sockets.

An example of this is with the new cellphones. Normally most of the phones have a universal port (3.5mm) for headphones. So their connection is made directly.
With the new cellphones, the companies decided to remove the headphone port, leaving only the charging port.

Here is where the adapter comes into play. Companies made an adapter so you can still use the 3.5mm headphones using the charging port.

Now that we understand better what is the Adaptor Pattern, I present you a JavaScript example.

Imagine that we decided to create a Calculator. This calculator needs three attributes (num1, num2, operation), the last one is in charge of the operation that will be realized.

class Calculator {
  operation(num1, num2, operation) {
    switch (operation) {
      case 'multiplication':
        return num1 * num2;
      case 'division':
        return num1 / num2;
      default:
        return NaN;
    }
  }
}

export default Calculator;
Enter fullscreen mode Exit fullscreen mode

and we can use the class like this:

import Calculator from "./Calculator"

const calculator = new Calculator();
const multi = calculator.operation(1, 2, 'multiplication');
console.log(multi ); //output 2

const div = calculator.operation(10, 2, 'division');
console.log(div); //output 5
Enter fullscreen mode Exit fullscreen mode

The time passes and the project gets bigger and bigger. It's time for a complete refactor of the Calculator class!

class Calculator {
  add(num1, num2) {
    return num1 + num2;
  }
  div(num1, num2) {
    return num1 / num2;
  }
  mult(num1, num2) {
    return num1 * num2;
  }
}

export default Calculator;
Enter fullscreen mode Exit fullscreen mode

This is the new way of using the calculator:

import Calculator from "./Calculator"

const calculator = new Calculator();
const sum = calculator.add(1, 2);
console.log(sum); //output 3

const sub = calculator.div(10, 2);
console.log(sub); //output 5
Enter fullscreen mode Exit fullscreen mode

As we can see, the refactor is no more compatible with the last version. For this we need to create an adaptor to make it work with both versions.

import Calculator from "./Calculator";

class CalculatorAdapter {
  constructor() {
    this.calculator = new Calculator();
  }
  operation(num1, num2, operation) {
    switch (operation) {
      case "add":
        return this.calculator.add(num1, num2);
      case "multiplication":
        return this.calculator.mult(num1, num2);
      case "division":
        return this.calculator.div(num1, num2);
      default:
        return NaN;
    }
  }
}

export default CalculatorAdapter;
Enter fullscreen mode Exit fullscreen mode

Now we can use the the original Calculator with the Adapter.

import Calculator from "./Calculator";
import CalculatorAdapter from "./CalculatorAdapter";

//Adapter
const calcAdapter = new CalculatorAdapter();
const sumAdapter = calcAdapter.operation(2, 2, "multiplication");
console.log(sumAdapter); //output 4

//Calculator
const calculator = new Calculator();
const sum = calculator.mult(2, 2);
console.log(sum); //output 4
Enter fullscreen mode Exit fullscreen mode

What are the pros and cons of this pattern?
Pros

  • It works with SOLID principles
  • We can add new adapters without braking the existing code.

Cons

  • The complexity of the code increases. This due the necessity of introducing new interfaces and classes.

Thanks for reading! Feel free to leave your feedback and love.

Have a great time and see you in future posts. 🔥

Top comments (4)

Collapse
 
jamesrweb profile image
James Robb • Edited

Probably the simplest example of this pattern I’ve seen in a while with a great example too, nicely done! 👌

Collapse
 
wecarrasco profile image
Walther Carrasco

Thanks James!

Collapse
 
sowmenappd profile image
Sowmen Rahman

Nice intro!

Collapse
 
wecarrasco profile image
Walther Carrasco

Thanks Sowmen!