+1  A: 
function validateZip() { // use function declaration, not function expression

    var lastSuccessful = parseInt(jQuery('#mailingZip').val(), 10);

    return {
        validate: function(zip) {
            var is5DigitNumber = /^\d{5}$/;
            if (is5DigitNumber.test(zip) && lastSuccessful !== zip) {
                lastSuccessful = zip;
                return true;
            } else {
                return false;
            }
        }
}; // removed premature invocation of function

jQuery(validateZip); // call it on document ready instead
NickFitz
A: 

Why can't you call it in ready event? Of course you can enclose it into another function:

$(functon(){

    var validateZip = function () {

        var lastSuccessful = parseInt(jQuery('#mailingZip').val(), 10);

        return {
            validate: function(zip) {
                var is5DigitNumber = /^\d{5}$/;
                if (is5DigitNumber.test(zip) && lastSuccessful !== zip) {
                    lastSuccessful = zip;
                    return true;
                } else {
                    return false;
                }
            }
    }();

});

The question is you you need to keep validateZip function as defined global? If you only run it at this point, just omit its declaration and just write:

$(functon(){

    (function () {

        var lastSuccessful = parseInt(jQuery('#mailingZip').val(), 10);

        return {
            validate: function(zip) {
                var is5DigitNumber = /^\d{5}$/;
                if (is5DigitNumber.test(zip) && lastSuccessful !== zip) {
                    lastSuccessful = zip;
                    return true;
                } else {
                    return false;
                }
            }
    })();

});
Robert Koritnik
Yes, the validateZip function needs to remain global -- I need to be able to call validateZip.validate(userValue), as this is triggered on keyup, as the user inputs into the field the function will be called, when the user inputs 5 digits an Ajax call is made. Let's say they submit the form and there is an error on another field, and this page is reloaded. I want to get the value from the dom, and set that as lastSuccessful. This way further calls are blocked if zip remains same.
Scott
A: 

Don't know why I didn't think / do this before. I created a getter/setter on my return function, then on the document ready just called the setter with that value.

var validateZip = function() {

// Track the last sent in zip code -- treat this as private data
var lastSuccessful = "";

return {
    validate : function(zip) {
        var is5DigitNumber = /^\d{5}$/;
        if (is5DigitNumber.test(zip) && lastSuccessful !== zip) {
            lastSuccessful = zip;
            return true;
        } else {
            return false;
        }
    },

    setLastSuccessful : function(zip) {
        lastSuccessful = zip;
    },

    getLastSuccessful : function() {
        return lastSuccessful;
    }
}

}();

jQuery(document).ready( function() { validateZip.setLastSuccessful(jQuery('#mailingZip').val()); });

Scott