var RoutingGenerator = function() {
    var defaultOptions = {
        method: "GET",
        beforeCallBack: function () {},
        successCallBack: function () {},
        errorCallBack: function () {},
        completeCallBack: function () {}
    };

    var routingEntities = [];

    var configureOptions = function (options) {
        if (typeof options !== "object") {
            return defaultOptions;
        }

        defaultOptions = Object.assign(defaultOptions, options);
    };

    var generate = function (id, entityClass, locale) {
        if (typeof routingEntities[id] !== "undefined") {
            handleCallBack(defaultOptions.successCallback, routingEntities[id]);
            handleCallBack(defaultOptions.completeCallBack, routingEntities[id]);

            return routingEntities[id];
        } else {
            $.ajax({
                url: Routing.generate("cs_core_links_generate"),
                method: defaultOptions.method,
                data: {
                    "id": id,
                    "className": entityClass,
                    "locale": locale
                },
                beforeSend: function (call) {
                    handleCallBack(defaultOptions.beforeCallBack, call);

                },
                success: function (response) {
                    routingEntities[id] = response;

                    handleCallBack(defaultOptions.successCallback, response);

                    return response;
                },
                error: function (response) {
                    handleCallBack(defaultOptions.errorCallBack, response);
                },
                complete: function (response) {
                    handleCallBack(defaultOptions.completeCallBack(), response);
                }
            });
        }
    };

    var handleCallBack = function (callBack, data) {
        if (typeof callBack === "function") {
            callBack.call(this, data);
        }
    };

    return {
        generate: function(id, entityClass, locale, options) {
            configureOptions(options);

            return generate(
                id,
                entityClass,
                locale
            );
        }
    };
}();