We will start by creating 2 objects, that are persons with a single property. Their Age and we want to have functionality to make these people get older by 1 year at a time so we add 1 to each of our persons age.
var amy = {age:33}; var ben = {age:26}; amy.age++; ben.age++; console.log(ben.age); // -> 27
Refactored step 1:
We will start with creating a function called ageing as this a functionality shared by all persons:
var ageing = function(person) { person.age++; }; var amy = {age:33}; var ben = {age:26}; ageing(amy); ageing(ben); console.log(ben.age); // -> 27
Refactor step 2:
As all our persons share the same properties we would want to create an object model that they can inherit these properties from.
var person = function(obj, age){ obj.age = age; return obj; }; var ageing = function(person) { person.age++; }; var amy = person({}, 33); var ben = person({}, 26); ageing(amy); ageing(ben); console.log(ben); // [object Object] {age:27}
Refactor step 3:
Now we add in the function of ageing to the object model so all objects will have this functionality
var person= function(obj, age){ obj.age = age; obj.ageing = ageing; return obj; }; var ageing = function(){ this.age += 1; }; var amy = person({}, 33); var ben = person({}, 26); amy.ageing(); ben.ageing(); console.log(ben.age); //27
Refactoring step 4:
Now we move in the function of ageing into the actual object which makes it were clear the the ageing process is something connected to persons.
var person = function(obj, age){ obj.age = age; obj.ageing = function() { this.age += 1; }; return obj; }; var amy = person({}, 33); var ben = person({}, 26); amy.ageing(); ben.ageing(); console.log(ben.age); //27
This might be a bit easier to read but have a lot of issues as now every time a objekt of person is created there will also be a new function created with it, which is unnecessary and not effective code.
Refactoring step 5:
because each object got its own closure around the ageing function there is no need for this anymore and we can use the obj instead:
var personlike = function(obj, age){ obj.age = age; obj.ageing = function() { obj.age += 1; } return obj; }; var amy = personlike({}, 33); var ben = personlike({}, 26); amy.ageing(); ben.ageing(); console.log(ben.age); //27
That’s it for the Object Decorater Pattern.
As mentioned there is issues with it and a more common use is the Constructor / Prototype pattern that eliminates these issues. You’ll find more about objects and different patterns in the article about JavaScript Objects.