Path: csiph.com!newsfeed.hal-mli.net!feeder3.hal-mli.net!weretis.net!feeder4.news.weretis.net!feeder1.news.weretis.net!news.solani.org!.POSTED!not-for-mail From: Thomas 'PointedEars' Lahn Newsgroups: comp.lang.javascript Subject: Re: Bind custom function to the all Function objects Date: Sat, 14 Jun 2014 15:55:46 +0200 Organization: PointedEars Software (PES) Lines: 126 Message-ID: <1859569.COELiHlnRc@PointedEars.de> References: <98e91$539b0b89$6def49ce$21580@nntpswitch.blueworldhosting.com> <1649322.pjBWu2vbqe@PointedEars.de> <94a15$539b16e4$6def49ce$21821@nntpswitch.blueworldhosting.com> <2459085.3y454gxjXg@PointedEars.de> <1e6b6$539b6200$6def49ce$25031@nntpswitch.blueworldhosting.com> <1464959.oZ30Yp1K6V@PointedEars.de> Reply-To: Thomas 'PointedEars' Lahn Mime-Version: 1.0 Content-Type: text/plain; charset="ISO-8859-1" Content-Transfer-Encoding: 7Bit X-Trace: solani.org 1402754148 14872 eJwFwYEBwCAIA7CXAGk7zhkq/59ggkXnVhJMDObySwXQoK5FdZdcSPSv2gEy5kSf9khbsgcDPRAX (14 Jun 2014 13:55:48 GMT) X-Complaints-To: abuse@news.solani.org NNTP-Posting-Date: Sat, 14 Jun 2014 13:55:48 +0000 (UTC) User-Agent: KNode/4.12.4 X-User-ID: eJwNxckBwDAIA7CVOGpDxglQ9h+h1UdwKjsegg8W6zJ1gNYytzPLCU2/lN6WbFTHrkmy8uLtgaea8U9co+QDUOoU9w== Face: iVBORw0KGgoAAAANSUhEUgAAADAAAAAwBAMAAAClLOS0AAAAGFBMVEXTxa4RFk5dUWANED8PFEfy7+MGBiW+n3ZNF/QuAAACaElEQVQ4jVXUwVOcMBQG8Dc7Rc4PUntdWV2uxjDpGaGeozOp1woar4jd5t/v9wLstMwsA/ntlxdCAgUc1hjTc9/JCZfGoo3wG3HdmdAWrIJRHe7GM/TmpY5VFefuVcAkkPbLIaN8rmPmjloyZxgyR3GuJ4K0AGtJ2htz8o7yqikm759fldQXaMpbDzjKAG+8v+AugVTOPO5DOjLvGtUYQwh0CPjnVMyGd+8/GfUB5nLKJDD2aLDh5HYyMDJGDwQIo2ZmZcKbowNmAdB/AzyFhrmF2MHRb0QJJfaAnwGB6orZhoykLzJtGwF/xpYxI1dswomiUj3gTuAIqCn/4C7cULwGNBtwMTk3Y4LfKB5YUaOKBKYtpplm7u0vip8tU1NWWyI/7XdcSuIDoMt6rVHMWT0DbjHPGqDqZVSa6zleLcUTcIKLoMv3ueJluALtAo9B302zPPlrtiVScRdCjXvVh3e3JpYa/jjkuC9N+LrBMlz/eAN4eQijX2EdLo6c5tGGHwLyHFtXk89dDGHwCVhG9T0S/j55AhRZgkMCmUQXJ49TnS1wnQDvw0eAh9ICeMmEFbCnPMFzjAvsWoEWEFdYEx+S0MoUZ1gT1wId8+AF3Bl2OoEu906AUHx5VLw/gXYg/x84loOah/2UYNrgiwSwGO7RfUzVBbx/kgpckumGOi6QirtD6gkLTitbnxNol47S2jVc2vsN5kPqaAHT8uUdAJM4v/DanjYOwmUjWznGfwB7sGtAtor5BgofDuzaRj4kSQAqDakTsKORa3Q3xKi3gE1fhl71KRMqrdZ2AWNNg/YOhQyrVBnb+i+nEg4bsDA+egAAAABJRU5ErkJggg== X-Face: %i>XG-yXR'\"2P/C_aO%~;2o~?g0pPKmbOw^=NT`tprDEf++D.m7"}HW6.#=U:?2GGctkL,f89@H46O$ASoW&?s}.k+&. Cezary Tomczyk wrote: >> However, I think that in reality it's not possible to do that because >> then changes needs to be done everywhere in the code. So, I thought that >> it would be better to "wrap" every function/method globally (not sure if >> I described it correctly) so that every call of function/method in web >> application first will call custom function before and put information's >> from console.count. In that way I could measure how many times every >> function/method is called. That's my goal. > > It is possible to wrap all *your* functions (that you *know*) simply by > replacing them (I do something similar in jsx.dom.addEventListener() in > order to emulate EventTarget::addEventListener() when unavailable): > > var myFunction = function () { > console.log("myFunction"); > }; > > /** > * Adds a call counter to a function. > * > * NOTE: Must pass object reference and property name for a general > * solution because there is no call-by-reference > * > * @param {Object} obj > * @param {String} propName > * @return {Function} > * Decorated function > */ > function addCounter (obj, propName) > { > var original_function = obj[propName]; > > if (typeof original_function != "function") > { > throw new TypeError( > "addCounter: obj[propName] must refer to a function"); > } > > var decorated = function () { > console.count("myFunction"); > original_function.apply(this, arguments); > }; > > obj[propName] = decorated; > > return decorated; > } > > /* > * Example: in global context; cannot generally decorate local functions > */ > addCounter(this, "myFunction"); Slight improvement (untested): /** * Decorates a function with code to be executed before and/or after * it is called. * * @param {Object|Function} obj * @param {String|Null|Undefined} propName * @param {Function} before * Code to be executed before the original function. Called with * the same this value and arguments as the original * function. * @param {Function} after (optional) * Code to be executed after the original function. Called with * the same this value as the original function. * The arguments lists consists of the return value of the * original function followed by its argument list. * @return {Function} Decorated function */ function decorate (obj, propName, before, after) { var original = (propName == null ? obj : obj[propName]); if (typeof original != "function") { throw new TypeError( "decorate: obj[propName] or obj must refer to a function"); } var decorated = function () { if (typeof before == "function") { before.apply(this, arguments); } var result = original.apply(this, arguments); if (typeof after == "function") { after.apply(this, [result].concat([].slice.call(arguments))); } }; if (propName != null) { obj[propName] = decorated; } return decorated; } /* * Example: in global context; cannot generally decorate local functions */ myFunction = decorate(myFunction, null, function () { console.count("myFunction"); }); decorate(foo, "bar", function () { baz (); }, function (result) { bla(result); }); -- PointedEars FAQ: | SVN: Twitter: @PointedEars2 | ES Matrix: Please do not Cc: me. / Bitte keine Kopien per E-Mail.