Created
October 31, 2012 22:29
-
-
Save anonymous/3990372 to your computer and use it in GitHub Desktop.
Simple LightWeight OOP in Node.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
var inherits = require('util').inherits; | |
function Class(obj, options) { | |
function F() { | |
F.prototype.constructor.apply(this, arguments); | |
} | |
if (options && options.baseClass) { | |
inherits(F, options.baseClass); | |
} | |
for (var property in obj) { | |
var value = obj[property]; | |
F.prototype[property] = value; //extend the prototype to meet our "class" layout | |
} | |
return F; | |
} | |
var assert = require("assert"), | |
util = require('util'); | |
var Base = Class({ | |
constructor: function (text) { | |
this.text = text; | |
}, | |
getText: function () { | |
return this.text; | |
} | |
}); | |
var Derived = Class({ | |
constructor: function (text, prefix) { | |
Base.prototype.constructor.call(this, text); | |
this.prefix = prefix; | |
}, | |
getText: function () { | |
return this.prefix + Base.prototype.getText.apply(this) + this.prefix; | |
} | |
}, { | |
baseClass: Base | |
}); | |
var Derived2 = Class({ | |
constructor: function (text, prefix, color) { | |
Derived.prototype.constructor.call(this, text, prefix); | |
this.color = color; | |
}, | |
getText: function () { | |
return this.color + Derived.prototype.getText.apply(this); | |
}, | |
getColor: function () { | |
return this.color; | |
} | |
}, { | |
baseClass: Derived | |
}); | |
var base = new Base("base"), | |
derived = new Derived("derived", "!"), | |
derived2 = new Derived2("derived2", "!", "red"); | |
//mocha test suite, all tests pass. | |
describe('Class', function () { | |
describe('API', function () { | |
it('Class should be callable', function () { | |
assert.equal(typeof Class === "function", true); | |
}); | |
it('Class should return a function', function () { | |
assert.equal(typeof Base === "function", true); | |
assert.equal(typeof Derived === "function", true); | |
assert.equal(typeof Derived2 === "function", true); | |
}); | |
it('derived should have same interface as base', function () { | |
assert.equal(typeof base.getText === "function", true); | |
assert.equal(typeof base.getText === typeof derived.getText, true); | |
assert.equal(typeof base.getText === typeof derived2.getText, true); | |
}); | |
}); | |
describe('Functional', function () { | |
it('base should be an instanceof Base', function () { | |
assert.equal(base instanceof Base, true); | |
}); | |
it('derived should be an instanceof Derived', function () { | |
assert.equal(derived instanceof Derived, true); | |
}); | |
it('derived2 should be an instanceof Derived2', function () { | |
assert.equal(derived2 instanceof Derived2, true); | |
}); | |
it('derived should be an instanceof Base', function () { | |
assert.equal(derived instanceof Base, true); | |
}); | |
it('derived2 should be an instanceof Derived', function () { | |
assert.equal(derived2 instanceof Derived, true); | |
}); | |
it('base should NOT be an instanceof Derived', function () { | |
assert.equal(base instanceof Derived, false); | |
}); | |
describe('#getText', function () { | |
it('base.getText() should return "base"', function () { | |
assert.equal(base.getText(), "base"); | |
}); | |
it('derived.getText() should return "!derived!"', function () { | |
assert.equal(derived.getText(), "!derived!"); | |
}); | |
it('derived2.getText() should return "red!derived!"', function () { | |
assert.equal(derived2.getText(), "red!derived2!"); | |
}); | |
}); | |
}); | |
}); | |
// However. The return value from Class is 100% compatible with pure JavaScript inheritance, | |
// so we can replace to example the Derived and prototype with the following: | |
function Derived(text, prefix) { | |
Base.call(this, text); | |
this.prefix = prefix; | |
} | |
util.inherits(Derived, Base); | |
Derived.prototype.getText = function () { | |
return this.prefix + Base.prototype.getText.apply(this) + this.prefix; | |
}; | |
//without any tests fail. |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment