Created
September 21, 2012 15:26
-
-
Save thanpolas/3762164 to your computer and use it in GitHub Desktop.
Get a new instance of an Object (class) that's invocable - binded to a specific method
This file contains hidden or 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
/** | |
* The invocator function creates a new instance of the provided constructor | |
* which is also linked to a method that it contains. | |
* | |
* Check this fiddle for a live example: http://jsfiddle.net/thanpolas/Aky9Y/7/ | |
* | |
* Invocator only works for pseudo-classical type of classes (prototypical). | |
* | |
* Requires 'bind' and 'isFunction', currently use underscore's equivalents. | |
* | |
* A special property '_instance' is exposed in the returned function which references | |
* the new instance of the object (class) - so you can use it for 'instanceOf' comparisons | |
* | |
* Consider this use case: | |
* | |
* var classOne = function(){}; | |
* classOne.prototype.foo = function(){return 1;}; // a method of classOne | |
* classOne.prototype.bar = function(){return 2;}; // another method of classOne | |
* | |
* var instOne = invocator(classOne, 'foo'); | |
* | |
* // instOne() === instOne.foo(); | |
* // instOne.bar() === 2; | |
* | |
* @param {Function} parentCtor The constructor we will be invocating | |
* @param {string} methodName The target method name we want to apply on | |
* the created instance | |
* @param {Regex=} opt_prvRegex A regex that matches the methods and properties | |
* that are private, e.g. classOne.prototype._prv | |
* @return {Function} An instance of parentCtor, that when invoked executes the | |
* target method, and with all the public properties / methods | |
* exposed. | |
*/ | |
function invocator (parentCtor, methodName, opt_prvRegex) | |
{ | |
// if regex not defined, default is to match every | |
// string that is _ or starts with _ or ends with _ | |
var prvRegex = opt_prvRegex || /^(_|_.+|.+_)$/; | |
var selfObj = new parentCtor(); | |
if (!_.isFunction(selfObj[methodName])) { | |
throw new TypeError('methodName:' + methodName + ' is not of type Function'); | |
} | |
// create the capsule and assign the target method binded | |
// to the selfObject | |
var capsule = _.bind(selfObj[methodName], selfObj); | |
// go through all the properties and methods of the instance | |
for (var prop in selfObj) { | |
// check if not private | |
if (!prop.match(prvRegex)) { | |
// not private, check if func | |
if (_.isFunction(selfObj[prop])) { | |
capsule[prop] = _.bind(selfObj[prop], selfObj); | |
} else { | |
capsule[prop] = selfObj[prop]; | |
} | |
} | |
} | |
capsule._instance = selfObj; | |
return capsule; | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment