Skip to content

snippets

neonstalwart edited this page Jan 24, 2011 · 6 revisions

code snippets

Model Builder

var req = 'req',
    handler = {
        addProcessor: function (processor) {
            var handler = this,
                process = this.process;

            this.process = function (req) {
                return Promise.when(process.call(handler, req), function (res) {
                    return processor(req, res);
                });
            };
        },
        process: function (req) {
            return 'res';
        }
    },
    processor1 = function (req , res) {
        var dfd = new Promise.Deferred();
        setTimeout(function () {
            dfd.resolve(res  + ' contribution1');
        }, 500);
        console.log('processor1', this, arguments);
        return dfd.promise;
    },
    processor2 = function (req , res) {
        var dfd = new Promise.Deferred();
        setTimeout(function () {
            dfd.resolve(res + ' contribution2');
        }, 1500);
        console.log('processor2', this, arguments);
        return dfd.promise;
    },
    res;

handler.addProcessor(processor1);
handler.addProcessor(processor2);
res = handler.process(req);
console.log(res);
Promise.when(res, function (x) {
    console.log(x);
});

Logger

this would be wrapped in a facility that read from the configuration and applied the Logger as needed. for example:

var logFacility = {
    logger: new Logger(), // defined below
    processModel: function (model) {
        // if model says to add a logger then...
        var prop = model.isInstance ? 'instance' : 'ctor';

        model[prop] = this.logger.apply(model[prop], model.logger.selector, model.logger.advice);
    }
};

var Ctor = Compose(function (foo) {
        this.foo = foo;
    }, {
        bar: function () {
            console.log('bar');
            return 'bar function';
        },
        baz: function () {
            console.log('baz');
            return 'baz function';
        },
        boo: function () {
            throw new Error('boo hoo...');
        }
    }),
    obj = {
        foo: function () {
            console.log('foo');
        }
    },
    // this is the interesting part, the rest is just some tests
    Logger = Compose({
        apply: function (obj, selector, advice) {
            advice = typeof advice === 'function' ? {
                after: advice
            } : advice;
	
            var mixin = {},
                base = typeof obj === 'function' ? obj.prototype : obj,
                composer = typeof obj === 'function' ? Compose : Compose.create,
                prop;
                
            // TODO: take selector into account when creating mixin
            for (prop in base) {
                if (base.hasOwnProperty(prop) /* && something with selector */) {
                    mixin[prop] = Compose.around(function (original) {
                        return function () {
                            var ret;
            					
                            if (advice.before) {
                                advice.before.apply(this, arguments);
                            }
                            try {
                                ret = original.apply(this, arguments);
                                if (advice.afterReturning) {
                                    advice.afterReturning.call(this, ret);
                                }
                                return ret;
                            }
                            catch (e) {
                                if (advice.afterThrowing) {
                                    advice.afterThrowing.call(this, e);
                                }
                                // propogate the exception
                                throw e;
                            }
                            finally {
                                if (advice.after) {
                                    advice.after.call(this);
                                }
                            }
                        }
                    });
                }
            }
            return composer(obj, mixin);
        }
    }),
    logger = new Logger();
    
console.log('before applying logger');
var b = new Ctor('xyz');
console.log(b.foo);
b.bar();
b.baz();
obj.foo();
   
console.log('applying function advice');
var Another = logger.apply(Ctor, null, function () {
    console.log('function advice');
});
    
var obj2 = logger.apply(obj, null, function () {
    console.log('function advice');
});
    
var c = new Another('bbb');
console.log(c.foo);
c.bar();
c.baz();
obj2.foo();
    
console.log('applying object advice');
var advice = {
    before: function () {
        console.log('before advice', this, arguments);
    },
    after: function () {
        console.log('after advice', this, arguments);
    },
    afterReturning: function () {
        console.log('after returning advice', this, arguments);
    },
    afterThrowing: function () {
        console.log('after throwing advice', this, arguments);
    }
};
var YetAnother = logger.apply(Ctor, null, advice),
    obj3 = logger.apply(obj, null, advice);
	
var d = new YetAnother('xxx');
console.log(d.foo);
d.bar(2,3,4);
d.baz('dddd');
obj3.foo('??!??');
d.boo(':(');
Clone this wiki locally