Search code examples
javascriptmodule-pattern

Module pattern javascript not a function?


I am trying to make my javascript code adherent to a Module pattern which I am following here:

http://addyosmani.com/resources/essentialjsdesignpatterns/book/#modulepatternjavascript

This is my code currently, there are no syntax issues apart from the runtime call which says

loosetime.init() is not a function.

var loosetime = (function () {
    var looseconfig = {
        "format": "DD/MM/YY HH24:MM:SS.s",
        "value": "DD/MM/YY 00:00.00",
        "class": "input",
        "delims": ['/', '-', '_', '.', '|', ',', ' ', ':']
    };

    function loosetime(a, b, c, d, e) {
        var format = a;
        var appendLoc = b;
        var inputVal = c;
        var inputName = d;
        var inputClass = e;
        var inputLength;

        try {
            if (typeof(format) == 'undefined') {
                format = looseconfig.format;
            } else {
                format = parseDateTime(format);
            }

            try {
                if (typeof(inputVal) == 'undefined') {
                    inputVal = looseconfig.value;
                }

                inputLength = inputVal.length - 2;
                var input = document.createElement("input");
                input.setAttribute("name", inputName);
                input.setAttribute("maxlength", inputLength);
                input.setAttribute("size", inputLength);
                input.setAttribute("value", inputVal);
                input.setAttribute("type", "input");
                input.setAttribute("class", inputClass);
                input.setAttribute("onkeypress", "dateTimeRules(event)");
                input.setAttribute("onclick", "resetCursorPos(event)");
                input.setAttribute("loosetime", format);

                try {
                    var element = document.getElementById(appendLoc);

                    element.appendChild(input);
                } catch (e) {
                    window.alert("Error, no Element given to append loosetime to.")
                }
            } catch (e) {
                window.alert("Error, Value is invalid." + e.toString());
            }
        } catch (e) {
            window.alert("Error, Date format missing or invalid.");
        }
    }

    // other code here ...

    return {
        init: loosetime()
    }

    // end private closure then run the closure
    });

Ideally I just want loosetime to work, I don't want to explicitly call the constructor.

e.g. loosetime("foo", "bar", "etc", "yolo", "123321");

I am not sure what I am doing wrong, do I need to return the function itself rather than an alias?


Solution

  • There are two things wrong.

    First you need to make sure your module is a self invoking anonymous function (SIAF), a.k.a immediately invoked function expression (IIFE). You can find more info on this topic here.

    Second you can't invoke the loosetime function inside your module because it doesn't return anything. You need the value of the init key to be a reference to the loosetime function.

    var loosetime = (function () {
    
      // ...
    
      function loosetime(a, b, c, d, e) {
        // ...
      }
    
      // ...
    
      return {
        init: loosetime // Note that init has a reference to loosetime and we don't execute it.
      };
    
    })(); // Note that you're missing the execution parentheses.
    

    Now you can call init and the loosetime function inside your module will be executed.