Hacker News new | past | comments | ask | show | jobs | submit | aaditmshah's comments login

In my humble opinion the smallest classical OOP pattern is as follows:

    function defclass(prototype) {
        var constructor = prototype.constructor;
        constructor.prototype = prototype;
        return constructor;
    }
You may then use it as:

    var Rectangle = defclass({
        constructor: function (width, height) {
            this.height = height;
            this.width = width;
        },
        area: function () {
            return this.width * this.height;
        }
    });
The only problem is that this doesn't support inheritance which is why I created `augment`. While creating `augment` I kept the following things in mind:

1. I didn't want to use a `for..in` loop to copy all the methods of the "class". Hence I used a function instead of an object to model the prototype.

2. Using a function instead of an object to model the prototype is similar to the module pattern. In addition you can create private static properties of a class (such as configuration) easily.

3. I wanted `augment` to work for both the [constructor pattern and the prototypal pattern](http://stackoverflow.com/a/16872315/783743) which is why `base` may be either a function or an object.

4. I wanted `augment` to be able to create singleton instances (again in the spirit of the prototypal pattern of prototypal inheritance). Hence I simply return the prototype if the "class" doesn't have a constructor.

Keeping these points in mind I added 4 more lines to the `defclass` function to create `augment`:

    function augment(base, body) {
        var uber = typeof base === "function" ? base.prototype : base;
        var prototype = Object.create(uber);
        body.apply(prototype, [].slice.call(arguments, 2).concat(uber));
        if (!prototype.hasOwnProperty("constructor")) return prototype;
        var constructor = prototype.constructor;
        constructor.prototype = prototype;
        return constructor;
    }
The above function is essentially the `augment` function in my GitHub repository minus the following features:

1. It's not defined as a method of `Function.prototype` or `Object.prototype`. Hence you can't call it as a method on a function or an object. I added this feature for flexibility of style. In retrospect I believe that it's unnecessary and hence I'll remove it.

2. It won't work in browsers which don't support and haven't patched `Object.create`. I understand that the patch my library provides is incomplete. In my defense I never thought that it would become infamous overnight. I'll fix this as well.

3. It doesn't use `bindable`, `callable` and other functional features I commonly use in my code. When I created `augment` I never expected many people to use it. Hence I put in all the functional features I commonly use in all my programs.

4. It doesn't use the `{}.hasOwnProperty.call` hack. Again I programmed defensively in my library. However I doubt that JavaScript programmers usually create classes which don't inherit from `Object.prototype`. Hence I'll remove that hack as well.

In short I'll remove all the unnecessary features from `augment` that I commonly use and deliver the smallest classical OOP library as promised.


Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: