commit
7cee1cf40e
25
Makefile
25
Makefile
|
@ -5,6 +5,10 @@ PATH_TOOLS=${CWD}/tools
|
|||
PATH_COMBINE_OUTPUT=${PATH_BUILD}/ease.js
|
||||
PATH_COMBINE_OUTPUT_FULL=${PATH_BUILD}/ease-full.js
|
||||
PATH_BROWSER_TEST=${PATH_TOOLS}/browser-test.html
|
||||
PATH_TEST=./test
|
||||
PATH_PERF_TEST=${PATH_TEST}/perf
|
||||
|
||||
PERF_TESTS := $(shell find "$(PATH_PERF_TEST)" -name 'perf-*.js')
|
||||
|
||||
PATH_DOC=${CWD}/doc
|
||||
PATH_DOC_OUTPUT=${PATH_BUILD}/doc
|
||||
|
@ -17,11 +21,14 @@ PATH_MANUAL_TEXI=${PATH_DOC}/manual.texi
|
|||
|
||||
COMBINE=${PATH_TOOLS}/combine
|
||||
|
||||
TESTS_JS := $(shell find "./test" -name 'test-*.js')
|
||||
TESTS_SHELL := $(shell find "./test" -name 'test-[^\.]*')
|
||||
TESTS := $(shell find "$(PATH_TEST)" \
|
||||
-name 'test-*' \
|
||||
-a ! -name 'test-combine.js'\
|
||||
)
|
||||
TEST_COMBINE := $(PATH_TEST)/test-combine.js
|
||||
|
||||
|
||||
.PHONY: test doc
|
||||
.PHONY: test test-combine doc
|
||||
|
||||
|
||||
default: combine
|
||||
|
@ -39,11 +46,17 @@ combine: mkbuild
|
|||
cp "${PATH_BROWSER_TEST}" "${PATH_BUILD}"
|
||||
|
||||
# run tests
|
||||
test: default $(TESTS_JS) $(TESTS_SHELL)
|
||||
test: default $(TESTS) test-combine
|
||||
test-combine: default $(TEST_COMBINE)
|
||||
test-%.js: default
|
||||
node $@
|
||||
node $@
|
||||
test-%: default
|
||||
./$@
|
||||
./$@
|
||||
|
||||
# performance tests
|
||||
perf: default $(PERF_TESTS)
|
||||
perf-%.js: default
|
||||
@node $@
|
||||
|
||||
# generate texinfo documentation (twice to generate TOC), then remove the extra
|
||||
# files that were generated
|
||||
|
|
3
TODO
3
TODO
|
@ -5,6 +5,9 @@
|
|||
[ target: 0.1.0 ]
|
||||
Misc
|
||||
- Class module is becoming too large; refactor
|
||||
- Disallow member redeclaration in definition
|
||||
- Permit binding on class methods
|
||||
- Provide ability to free class from memory (class data stored in internal vars)
|
||||
|
||||
Member Keywords
|
||||
- Restrictions; throw exceptions when unknown keywords are used
|
||||
|
|
60
lib/class.js
60
lib/class.js
|
@ -457,6 +457,9 @@ var extend = ( function( extending )
|
|||
}
|
||||
}
|
||||
|
||||
// increment class identifier
|
||||
class_id++;
|
||||
|
||||
util.propParse( props, {
|
||||
each: function( name, value, keywords )
|
||||
{
|
||||
|
@ -498,7 +501,8 @@ var extend = ( function( extending )
|
|||
method: function( name, func, is_abstract, keywords )
|
||||
{
|
||||
member_builder.buildMethod(
|
||||
members, null, name, func, keywords, getMethodInstance
|
||||
members, null, name, func, keywords, getMethodInstance,
|
||||
class_id
|
||||
);
|
||||
|
||||
if ( is_abstract )
|
||||
|
@ -531,13 +535,13 @@ var extend = ( function( extending )
|
|||
// set up the new class
|
||||
var new_class = createCtor( cname, abstract_methods, members );
|
||||
|
||||
attachPropInit( prototype, prop_init, members );
|
||||
attachPropInit( prototype, prop_init, members, class_id );
|
||||
|
||||
new_class.prototype = prototype;
|
||||
new_class.constructor = new_class;
|
||||
|
||||
// important: call after setting prototype
|
||||
setupProps( new_class, abstract_methods, ++class_id );
|
||||
setupProps( new_class, abstract_methods, class_id );
|
||||
|
||||
// lock down the new class (if supported) to ensure that we can't add
|
||||
// members at runtime
|
||||
|
@ -761,24 +765,27 @@ function initInstance( iid, instance )
|
|||
* ensuring that their data is not shared with other instances (this is not a
|
||||
* problem with primitive data types).
|
||||
*
|
||||
* The __initProps() method will also initialize any parent properties
|
||||
* (recursive) to ensure that subtypes do not have a referencing issue, and
|
||||
* subtype properties take precedence over those of the parent.
|
||||
* The method will also initialize any parent properties (recursive) to ensure
|
||||
* that subtypes do not have a referencing issue, and subtype properties take
|
||||
* precedence over those of the parent.
|
||||
*
|
||||
* @param {Object} prototype prototype to attach method to
|
||||
* @param {Object} properties properties to initialize
|
||||
* @param {number} cid class id
|
||||
*
|
||||
* @param {{public: Object, protected: Object, private: Object}} members
|
||||
*
|
||||
* @return {undefined}
|
||||
*/
|
||||
function attachPropInit( prototype, properties, members )
|
||||
function attachPropInit( prototype, properties, members, cid )
|
||||
{
|
||||
util.defineSecureProp( prototype, '__initProps', function( inherit )
|
||||
{
|
||||
// defaults to false
|
||||
// defaults to false, sid = super identifier
|
||||
inherit = !!inherit;
|
||||
|
||||
var iid = this.__iid;
|
||||
|
||||
// first initialize the parent's properties, so that ours will overwrite
|
||||
// them
|
||||
var parent_init = prototype.parent.__initProps;
|
||||
|
@ -790,21 +797,17 @@ function attachPropInit( prototype, properties, members )
|
|||
parent_init.call( this, true );
|
||||
}
|
||||
|
||||
// this will return our property proxy, if supported by our environment,
|
||||
// otherwise just a normal object with everything merged in
|
||||
var inst_props = propobj.createPropProxy(
|
||||
this, class_instance[ this.__iid ], properties[ 'public' ]
|
||||
this, class_instance[ iid ], properties[ 'public' ]
|
||||
);
|
||||
|
||||
// use whatever was returned by the property proxy (which may not be a
|
||||
// proxy, depending on JS engine support)
|
||||
class_instance[ this.__iid ] = inst_props;
|
||||
|
||||
// if we're inheriting, perform a setup that doesn't include everything
|
||||
// that we don't want (e.g. private properties)
|
||||
var setup = ( inherit )
|
||||
? propobj.setupInherited
|
||||
: propobj.setup
|
||||
;
|
||||
setup( inst_props, properties, members );
|
||||
class_instance[ iid ][ cid ] = propobj.setup(
|
||||
inst_props, properties, members
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -981,21 +984,28 @@ function getMeta( id )
|
|||
/**
|
||||
* Returns the instance object associated with the given method
|
||||
*
|
||||
* The instance object contains the protected and private members. This object
|
||||
* can be passed as the context when calling a method in order to give that
|
||||
* method access to those members.
|
||||
* The instance object contains the protected members. This object can be passed
|
||||
* as the context when calling a method in order to give that method access to
|
||||
* those members.
|
||||
*
|
||||
* One level above the instance object on the prototype chain is the object
|
||||
* containing the private members. This is swappable, depending on the class id
|
||||
* associated with the provided method call. This allows methods that were not
|
||||
* overridden by the subtype to continue to use the private members of the
|
||||
* supertype.
|
||||
*
|
||||
* @param {function()} method method to look up instance object for
|
||||
* @param {number} cid class id
|
||||
*
|
||||
* @return {Object,null} instance object if found, otherwise null
|
||||
*/
|
||||
function getMethodInstance( method )
|
||||
function getMethodInstance( inst, cid )
|
||||
{
|
||||
var iid = method.__iid,
|
||||
data = class_instance[ method.__iid ];
|
||||
var iid = inst.__iid,
|
||||
data = class_instance[ iid ];
|
||||
|
||||
return ( iid && data )
|
||||
? data
|
||||
? data[ cid ]
|
||||
: null
|
||||
;
|
||||
}
|
||||
|
|
|
@ -62,11 +62,12 @@ exports.initMembers = function( mpublic, mprotected, mprivate )
|
|||
|
||||
* @param {Object=} instCallback function to call in order to retrieve
|
||||
* object to bind 'this' keyword to
|
||||
* @param {number} cid class id
|
||||
*
|
||||
* @return {undefined}
|
||||
*/
|
||||
exports.buildMethod = function(
|
||||
members, meta, name, value, keywords, instCallback
|
||||
members, meta, name, value, keywords, instCallback, cid
|
||||
)
|
||||
{
|
||||
var prev;
|
||||
|
@ -109,7 +110,7 @@ exports.buildMethod = function(
|
|||
if ( prev )
|
||||
{
|
||||
// override the method
|
||||
dest[ name ] = overrideMethod( prev, value, instCallback );
|
||||
dest[ name ] = overrideMethod( prev, value, instCallback, cid );
|
||||
}
|
||||
else if ( keywords[ 'abstract' ] )
|
||||
{
|
||||
|
@ -120,7 +121,7 @@ exports.buildMethod = function(
|
|||
{
|
||||
// we are not overriding the method, so simply copy it over, wrapping it
|
||||
// to ensure privileged calls will work properly
|
||||
dest[ name ] = overrideMethod( value, null, instCallback );
|
||||
dest[ name ] = overrideMethod( value, null, instCallback, cid );
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -303,10 +304,11 @@ function scanMembers( members, name, cmp )
|
|||
*
|
||||
* @param {Object=} instCallback function to call in order to retrieve
|
||||
* object to bind 'this' keyword to
|
||||
* @param {number} cid class id
|
||||
*
|
||||
* @return {function()} override method
|
||||
*/
|
||||
function overrideMethod( super_method, new_method, instCallback )
|
||||
function overrideMethod( super_method, new_method, instCallback, cid )
|
||||
{
|
||||
instCallback = instCallback || function() {};
|
||||
|
||||
|
@ -319,7 +321,7 @@ function overrideMethod( super_method, new_method, instCallback )
|
|||
{
|
||||
override = function()
|
||||
{
|
||||
var context = instCallback( this ) || this,
|
||||
var context = instCallback( this, cid ) || this,
|
||||
retval = undefined
|
||||
;
|
||||
|
||||
|
@ -344,7 +346,7 @@ function overrideMethod( super_method, new_method, instCallback )
|
|||
// we are defining a new method
|
||||
override = function()
|
||||
{
|
||||
var context = instCallback( this ) || this,
|
||||
var context = instCallback( this, cid ) || this,
|
||||
retval = undefined
|
||||
;
|
||||
|
||||
|
|
|
@ -31,43 +31,37 @@ var util = require( './util' ),
|
|||
|
||||
|
||||
/**
|
||||
* Sets up properties when inheriting
|
||||
* Sets up properties (non-inheriting)
|
||||
*
|
||||
* This does not include private members.
|
||||
* This includes all members (including private). Private members will be set up
|
||||
* in a separate object, so that they can be easily removed from the mix. That
|
||||
* object will include the destination object in the prototype, so that the
|
||||
* access should be transparent. This object is returned.
|
||||
*
|
||||
* @param {Object} dest destination object
|
||||
* @param {Object} properties properties to copy
|
||||
* @param {Object=} methods methods to copy
|
||||
*
|
||||
* @return {undefined}
|
||||
* @return {Object} object containing private members and dest as prototype
|
||||
*/
|
||||
exports.setupInherited = function( dest, properties, methods )
|
||||
exports.setup = function( dest, properties, methods )
|
||||
{
|
||||
// this constructor is an extra layer atop of the destination object, which
|
||||
// will contain the private methods
|
||||
var obj_ctor = function() {};
|
||||
obj_ctor.prototype = dest;
|
||||
|
||||
var obj = new obj_ctor();
|
||||
|
||||
// initialize each of the properties for this instance to
|
||||
// ensure we're not sharing references to prototype values
|
||||
doSetup( dest, properties[ 'public' ] );
|
||||
doSetup( dest, properties[ 'protected' ], methods[ 'protected'] );
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Sets up properties (non-inheriting)
|
||||
*
|
||||
* This includes all members (including private).
|
||||
*
|
||||
* @param {Object} dest destination object
|
||||
* @param {Object} properties properties to copy
|
||||
* @param {Object=} methods methods to copy
|
||||
*
|
||||
* @return {undefined}
|
||||
*/
|
||||
exports.setup = function( dest, properties, methods )
|
||||
{
|
||||
// first, set up the public and protected members
|
||||
exports.setupInherited( dest, properties, methods );
|
||||
|
||||
// then add the private parts
|
||||
doSetup( dest, properties[ 'private' ], methods[ 'private' ] );
|
||||
doSetup( obj, properties[ 'private' ], methods[ 'private' ] );
|
||||
|
||||
return obj;
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -0,0 +1,8 @@
|
|||
This directory contains the performance tests. These tests contain basic
|
||||
routines that perform a single action and output the result in seconds, with a
|
||||
basic description of what has been done. The timing is done via the native Date
|
||||
object to ensure that it can be run both server and client-side.
|
||||
|
||||
It is important that each test performs only a single operation to ensure that
|
||||
the prior operations have no consequences on the previous, at least when run
|
||||
server-side by invoking a separate executable for each.
|
|
@ -0,0 +1,99 @@
|
|||
/**
|
||||
* Common performance testing functionality
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
/**
|
||||
* Stores start time
|
||||
* @type {number}
|
||||
*/
|
||||
var start = 0;
|
||||
|
||||
|
||||
/**
|
||||
* Includes a module from the lib directory
|
||||
*
|
||||
* @param {string} name module name
|
||||
*
|
||||
* @return {Object} module exports
|
||||
*/
|
||||
exports.require = function( name )
|
||||
{
|
||||
return require( '../../lib/' + name );
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* A simple wrapper to perform testing and output the result
|
||||
*
|
||||
* The count is not used to call the function multiple times, because that would
|
||||
* greatly impact the test results. Instead, you should pass the number of times
|
||||
* the test was performed in a loop.
|
||||
*
|
||||
* @param {function()} test performance test to perform
|
||||
* @param {number} count number of times the test was performed
|
||||
* @param {string=} desc test description
|
||||
*
|
||||
* @return {undefined}
|
||||
*/
|
||||
exports.test = function( test, count, desc )
|
||||
{
|
||||
exports.start();
|
||||
test();
|
||||
exports.report( count, desc );
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Starts the timer
|
||||
*
|
||||
* @return {undefined}
|
||||
*/
|
||||
exports.start = function()
|
||||
{
|
||||
start = ( new Date() ).getTime();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Outputs the time elapsed, followed by the description (if available)
|
||||
*
|
||||
* @param {number} count number of times the test was performed
|
||||
* @param {string=} desc test description
|
||||
*
|
||||
* @return {undefined}
|
||||
*/
|
||||
exports.report = function( count, desc )
|
||||
{
|
||||
count = +count;
|
||||
desc = desc || '';
|
||||
|
||||
var end = ( new Date() ).getTime(),
|
||||
total = ( ( end - start ) / 1000 ).toFixed( 3 ),
|
||||
pers = ( total / count ).toFixed( 10 )
|
||||
;
|
||||
|
||||
console.log( total + "s (x" + count + " = " + pers + "s each)" +
|
||||
( ( desc ) ? ( ': ' + desc ) : '' )
|
||||
);
|
||||
};
|
||||
|
|
@ -0,0 +1,47 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes with a few members,
|
||||
* private keyword
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {
|
||||
'private a': function() {},
|
||||
'private b': function() {},
|
||||
'private c': function() {},
|
||||
} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' anonymous classes with private members' );
|
|
@ -0,0 +1,47 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes with a few members,
|
||||
* protected keyword
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {
|
||||
'protected a': function() {},
|
||||
'protected b': function() {},
|
||||
'protected c': function() {},
|
||||
} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' anonymous classes with protected members' );
|
|
@ -0,0 +1,47 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes with a few members, public
|
||||
* keyword
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {
|
||||
'public a': function() {},
|
||||
'public b': function() {},
|
||||
'public c': function() {},
|
||||
} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' anonymous classes with public members' );
|
|
@ -0,0 +1,47 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes with a few members, no
|
||||
* keywords
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {
|
||||
a: function() {},
|
||||
b: function() {},
|
||||
c: function() {},
|
||||
} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' anonymous classes with few methods' );
|
|
@ -0,0 +1,42 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( 'Foo', {} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' empty named classes' );
|
|
@ -0,0 +1,47 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes with a few properties,
|
||||
* private keyword
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {
|
||||
'private a': 'foo',
|
||||
'private b': 10,
|
||||
'private c': false,
|
||||
} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' anonymous classes with private properties' );
|
|
@ -0,0 +1,47 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes with a few properties,
|
||||
* protected keyword
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {
|
||||
'protected a': 'foo',
|
||||
'protected b': 10,
|
||||
'protected c': false,
|
||||
} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' anonymous classes with protected properties' );
|
|
@ -0,0 +1,47 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes with a few properties,
|
||||
* public keyword
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {
|
||||
'public a': 'foo',
|
||||
'public b': 10,
|
||||
'public c': false,
|
||||
} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' anonymous classes with public properties' );
|
|
@ -0,0 +1,47 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes with few properties, no
|
||||
* keywords
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {
|
||||
a: 'foo',
|
||||
b: 10,
|
||||
c: false,
|
||||
} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' anonymous classes with few properties' );
|
|
@ -0,0 +1,42 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare 1000 classes
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 1000
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Class( {} );
|
||||
}
|
||||
|
||||
}, count, 'Declare ' + count + ' empty anonymous classes' );
|
|
@ -0,0 +1,101 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare read properties internally and
|
||||
* externally
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' ),
|
||||
|
||||
// we need many tests for a measurable result
|
||||
count = 500000
|
||||
|
||||
// instance of anonymous class
|
||||
foo = Class( {
|
||||
'public pub_bar': 'foo',
|
||||
'protected prot_bar': 'bar',
|
||||
'private priv_bar': 'baz',
|
||||
|
||||
'public testInternal': function()
|
||||
{
|
||||
var _self = this;
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count,
|
||||
val = null
|
||||
;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
val = _self.pub_bar;
|
||||
}
|
||||
}, count, 'Read public properties internally' );
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count,
|
||||
val = null
|
||||
;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
val = _self.prot_bar;
|
||||
}
|
||||
}, count, 'Read protected properties internally' );
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count,
|
||||
val = null
|
||||
;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
val = _self.priv_bar;
|
||||
}
|
||||
}, count, 'Read private properties internally' );
|
||||
},
|
||||
} )()
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count,
|
||||
val = null
|
||||
;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
val = foo.pub_bar;
|
||||
}
|
||||
|
||||
}, count, 'Read public properties externally' );
|
||||
|
||||
|
||||
// run the same test internally
|
||||
foo.testInternal();
|
||||
|
|
@ -0,0 +1,43 @@
|
|||
/**
|
||||
* Tests amount of time taken to instantiate anonymous classes
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 5000,
|
||||
Foo = Class( {} )
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
Foo();
|
||||
}
|
||||
|
||||
}, count, 'Instantiate ' + count + ' empty anonymous classes' );
|
|
@ -0,0 +1,44 @@
|
|||
/**
|
||||
* Tests amount of time taken to instantiate named classes
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' )
|
||||
|
||||
count = 5000,
|
||||
Foo = Class( 'Foo', {} )
|
||||
;
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
// to be extra confident that V8 or another compiler won't realize this
|
||||
// is useless and optimize it out
|
||||
Foo();
|
||||
}
|
||||
|
||||
}, count, 'Instantiate ' + count + ' empty named classes' );
|
|
@ -0,0 +1,111 @@
|
|||
/**
|
||||
* Tests amount of time taken to invoke Class methods
|
||||
*
|
||||
* The expected results are as follows:
|
||||
* - Method invocations are expected to be slower than invoking a method on a
|
||||
* conventional constructor instance. This is because of the method wrapper
|
||||
* used by ease.js.
|
||||
* - Public methods externally should be invoked very quickly. They are part
|
||||
* of the class's prototype and therefore easily accessible.
|
||||
* - Public methods /internally/ are likely to be invoked slightly more
|
||||
* slowly. This is because it takes one extra step down the prototype chain
|
||||
* to access them. The difference should be minute.
|
||||
* - Protected and private methods internally should be accessed fairly
|
||||
* quickly since, like public methods externally, they are first on the
|
||||
* prototype chain.
|
||||
* - Protected members will be accessed more slowly than private members,
|
||||
* because they are one step lower on the prototype chain. Future versions
|
||||
* will remove this performance hit if the Class contains no private
|
||||
* members.
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' ),
|
||||
|
||||
count = 500000,
|
||||
|
||||
// used to ensure v8 doesn't optimize functions away
|
||||
i = 0,
|
||||
|
||||
// instance of anonymous class
|
||||
foo = Class( {
|
||||
'public pub': function() { i++; },
|
||||
'protected prot': function() { i++; },
|
||||
'private priv': function() { i++; },
|
||||
|
||||
'public testInternal': function()
|
||||
{
|
||||
var _self = this;
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
_self.pub();
|
||||
}
|
||||
}, count, 'Invoke public methods internally' );
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
_self.prot();
|
||||
}
|
||||
}, count, 'Invoke protected methods internally' );
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
_self.priv();
|
||||
}
|
||||
}, count, 'Invoke private methods internally' );
|
||||
},
|
||||
} )()
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
foo.pub();
|
||||
}
|
||||
|
||||
}, count, 'Invoke public methods externally' );
|
||||
|
||||
|
||||
// run the same test internally
|
||||
foo.testInternal();
|
||||
|
|
@ -0,0 +1,33 @@
|
|||
/**
|
||||
* Tests amount of time spent on requiring class module
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' );
|
||||
|
||||
// we run this test once because require() will cache the object in memory
|
||||
common.test( function()
|
||||
{
|
||||
common.require( 'class' );
|
||||
}, 1, 'Require class module' );
|
||||
|
|
@ -0,0 +1,101 @@
|
|||
/**
|
||||
* Tests amount of time taken to declare read properties internally and
|
||||
* externally
|
||||
*
|
||||
* Copyright (C) 2010 Mike Gerwitz
|
||||
*
|
||||
* This file is part of ease.js.
|
||||
*
|
||||
* ease.js is free software: you can redistribute it and/or modify it under the
|
||||
* terms of the GNU Lesser General Public License as published by the Free
|
||||
* Software Foundation, either version 3 of the License, or (at your option)
|
||||
* any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
|
||||
* for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @author Mike Gerwitz
|
||||
* @package performance
|
||||
*/
|
||||
|
||||
|
||||
var common = require( __dirname + '/common.js' ),
|
||||
Class = common.require( 'class' ),
|
||||
|
||||
// we need many tests for a measurable result
|
||||
count = 500000
|
||||
|
||||
// instance of anonymous class
|
||||
foo = Class( {
|
||||
'public pub_bar': 'foo',
|
||||
'protected prot_bar': 'bar',
|
||||
'private priv_bar': 'baz',
|
||||
|
||||
'public testInternal': function()
|
||||
{
|
||||
var _self = this;
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count,
|
||||
val = null
|
||||
;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
_self.pub_bar = 'foo';
|
||||
}
|
||||
}, count, 'Write public properties internally' );
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count,
|
||||
val = null
|
||||
;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
_self.prot_bar = 'foo';
|
||||
}
|
||||
}, count, 'Write protected properties internally' );
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count,
|
||||
val = null
|
||||
;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
_self.priv_bar = 'foo';
|
||||
}
|
||||
}, count, 'Write private properties internally' );
|
||||
},
|
||||
} )()
|
||||
;
|
||||
|
||||
|
||||
common.test( function()
|
||||
{
|
||||
var i = count,
|
||||
val = null
|
||||
;
|
||||
|
||||
while ( i-- )
|
||||
{
|
||||
foo.pub_bar = 'foo';
|
||||
}
|
||||
|
||||
}, count, 'Write public properties externally' );
|
||||
|
||||
|
||||
// run the same test internally
|
||||
foo.testInternal();
|
||||
|
|
@ -73,6 +73,24 @@ var common = require( './common' ),
|
|||
{
|
||||
// override me
|
||||
},
|
||||
|
||||
|
||||
'public getPrivProp': function()
|
||||
{
|
||||
return this.parts;
|
||||
},
|
||||
|
||||
|
||||
'public invokePriv': function()
|
||||
{
|
||||
return this._priv();
|
||||
},
|
||||
|
||||
|
||||
'private _priv': function()
|
||||
{
|
||||
return priv;
|
||||
},
|
||||
}),
|
||||
|
||||
// instance of Foo
|
||||
|
@ -80,13 +98,28 @@ var common = require( './common' ),
|
|||
|
||||
// subtype
|
||||
SubFoo = Foo.extend({
|
||||
'private _pfoo': 'baz',
|
||||
|
||||
'public getSelfOverride': function()
|
||||
{
|
||||
// return this from overridden method
|
||||
return this;
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* We have to override this so that 'this' is not bound to the supertype
|
||||
*/
|
||||
'public getProp': function( name )
|
||||
{
|
||||
// return property, allowing us to break encapsulation for
|
||||
// protected/private properties (for testing purposes)
|
||||
return this[ name ];
|
||||
},
|
||||
}),
|
||||
sub_foo = SubFoo()
|
||||
sub_foo = SubFoo(),
|
||||
|
||||
sub_sub_foo = SubFoo.extend( {} )()
|
||||
;
|
||||
|
||||
|
||||
|
@ -362,3 +395,50 @@ var common = require( './common' ),
|
|||
);
|
||||
} )();
|
||||
|
||||
|
||||
/**
|
||||
* This one's a particularly nasty bug that snuck up on me. Private members
|
||||
* should not be accessible to subtypes; that's a given. However, they need to
|
||||
* be accessible to the parent methods. For example, let's say class Foo
|
||||
* contains public method bar(), which invokes private method _baz(). This is
|
||||
* perfectly legal. Then SubFoo extends Foo, but does not override method bar().
|
||||
* Invoking method bar() should still be able to invoke private method _baz(),
|
||||
* because, from the perspective of the parent class, that operation is
|
||||
* perfectly legal.
|
||||
*
|
||||
* The resolution of this bug required a slight system redesign. The short-term
|
||||
* fix was to declare any needed private members are protected, so that they
|
||||
* were accessible by the subtype.
|
||||
*/
|
||||
( function testParentMethodsCanAccessPrivateMembersOfParent()
|
||||
{
|
||||
// properties
|
||||
assert.equal(
|
||||
sub_foo.getPrivProp(),
|
||||
priv,
|
||||
"Parent methods should have access to the private properties of the " +
|
||||
"parent"
|
||||
);
|
||||
|
||||
// methods
|
||||
assert.equal(
|
||||
sub_foo.invokePriv(),
|
||||
priv,
|
||||
"Parent methods should have access to the private methods of the parent"
|
||||
);
|
||||
|
||||
// should apply to super-supertypes too
|
||||
assert.equal(
|
||||
sub_sub_foo.getPrivProp(),
|
||||
priv,
|
||||
"Parent methods should have access to the private properties of the " +
|
||||
"parent (2)"
|
||||
);
|
||||
assert.equal(
|
||||
sub_sub_foo.invokePriv(),
|
||||
priv,
|
||||
"Parent methods should have access to the private methods of the " +
|
||||
"parent (2)"
|
||||
);
|
||||
} )();
|
||||
|
||||
|
|
Loading…
Reference in New Issue