Parasitic Inheritance

http://stackoverflow.com/questions/11675006

by klenwell

JavaScript

// see http://stackoverflow.com/questions/11675006

function Parasite(host) {
    var self = {};
    self.host = host;
    self.swollen = false;
    
    self.init = function() {
        console.debug('Parasite.init');
        return self;
    };
    
    self.suck = function() {
        console.log("I'm a parasite who sucks on " + self.host);
        self.swollen = true;
        return self;
    };
    
    self.extend = function(child) {
        child.parent = self;
        
        for(var prop in self) {
            if (prop == 'extend') {     // skip extend
                console.debug('skip extend');
                continue;
            }
        
            var is_extended = child.hasOwnProperty(prop);
            var is_func = typeof self[prop] == "function";
            
            // inherit prop
            if (! is_extended) {
                child[prop] = self[prop];
                console.debug('prop', prop, 'inherited by child');
            }
            // default: override
            else {
                console.debug('prop', prop, 'overridden by child');
            }
            
            // for non-function props, parent should reference child
            if (! is_func) {
                var prop_name = prop.toString();
                console.error('define setter/getter for', prop_name, 'ccv', child[prop_name]);
                Object.defineProperty(self, prop_name, {                      
                    get: function() {
                        //var name = prop_name;
                        console.debug('getting', prop_name, child[prop_name], this);
                        return child[prop_name];
                    },
                    set: function(val) { 
                        //var name = prop_name;
                        console.debug('setting', prop_name, val, child, this);
                        child[prop_name] = val;
                    }
                });
            };
        }

        
        return...