查询字符串始终返回相同的值 - JavaScript

时间:2010-10-12 18:47:03

标签: javascript ajax string

我不希望有人读取整个脚本,但你会注意到有一个带有insert()函数的sort对象,它返回一个使用三元运算符返回“-order_value”或“order_value”的对象“,其中order_value是一个保存值的局部变量。问题出现在查询字符串中,它总是传递“-order_value”而从不传递“order_value”。我认为问题是当调用ajax方法时,它总是实例化一个新的Table对象,因此所有变量都被擦除,而不是记住-order_value,它默认返回order_value。任何解决方案?

<script>
(function($){

var listview = $('#listview');

var lists = (function(){
    var criteria = {
        dropFilter: {
            insert: function(value){
                if(value)
                    return {"filter" : value}; 
            },
            msg: "Filtering..."
        },
        searchFilter: {
            insert: function(value){
                if(value)
                    return {"search" : value}
            },
            msg: "Searching..."
        },
        sort: {
            insert: function(order, page){
                arr = [];
                arr[arr.length] = order;
                arr[arr.length] = page;
                return function(order_value, page_value){  
                    var order_value = (order_value.indexOf("-") > -1) ? order_value : "-" + order_value;
                    var page_value = page_value;
                    return {order : order_value, page : page_value };
                }
            },
            msg: "Sorting..."
        }
    }
    return {  
         create: function(component){
            var component = component.href.substring(component.href.lastIndexOf('#') + 1); 
            return component;
        },
         setDefaults: function(component){
            var parameter = {};
            switch(component){
                case "sites":
                    parameter = {
                        'url': 'sites',                         
                        'order': 'site_num',
                        'per_page': '20'
                    }
            }
            return parameter;
        },
        getCriteria: function(criterion){
            return criteria[criterion];  

        },
        addCriteria: function(criterion, method){
            criteria[criterion] = method;  
        }
    }
})(); 

var Form = function(form){
    var fields = [];
    $(form[0].elements).each(function(){  
        var field = $(this);  
        if(typeof field.attr('alter-data') !== 'undefined') fields.push(new Field(field));  
    })  
}

Form.prototype = {
    initiate: function(){
        for(field in this.fields){
            this.fields[field].calculate();  
        }
    },
     isCalculable: function(){    
        for(field in this.fields){  
                if(!this.fields[field].alterData){  
                return false; 
            }
        } 
        return true;  
    } 
}

var Field = function(field){ 
    this.field = field; 
    this.alterData = true;  
    this.component = {'url' : window.location.hash.substring(window.location.hash.indexOf('#') + 1)};
    this.attach("change");  
    this.attach("keypress");  
}

Field.prototype = {  
    attach: function(event){
        var obj = this;  
        if(event == "change"){
            obj.field.bind("change", function(){  
                return obj.calculate();
            })
        }
        if(event == "keypress"){
            obj.field.bind("keypress", function(e){  
                var code = (e.keyCode ? e.keyCode : e.which);
                if(code == 13){ 
                    e.preventDefault();
                    return obj.calculate();
                }
            })
        }
    },
    calculate: function(){
        var obj = this,  
            field = obj.field,  
            component = obj.component,
            msgClass = "msgClass",
            msgList = $(document.createElement("ul")).addClass("msgClass"),  
            types = field.attr("alter-data").split(" "),  
            container = field.parent(),  
            messages = [];

        field.next(".msgClass").remove();  
        for(var type in types){  
            var criterion = lists.getCriteria(types[type]); 
            if(field.val()){  
                var result = criterion.insert(field.val()); 

                container.addClass("waitingMsg");  

                messages.push(criterion.msg);  

                obj.alterData = true; 

                initializeTable(component, result); 

            }
            else { 
                return false; 

                obj.alterData = false;  
            }
        }
        if(messages.length){
            for(msg in messages){
                msgList.append("<li>" + messages[msg] + "</li");  
            }
        }
        else{
            msgList.remove();  
        }
    }
}

var Table = function(table){
    headers = [];
    $(table[0].getElementsByTagName('th')).each(function(){
        var header = $(this);  
        if(typeof header.attr('data-sorter') !== 'undefined') headers.push(new Header(header)); 
    })
}

Table.prototype = {
    isSortable: function(){

    }
}

var Header = function(header){

    this.header = header;
    this.isSortable = true;
    this.component = {'url' : window.location.hash.substring(window.location.hash.indexOf('#') + 1)};
    this.fieldName = header.children()[0].href.substring(header.children()[0].href.lastIndexOf("/") + 1, header.children()[0].href.length); 
    this.attach('click'); 
}

Header.prototype = {
    attach: function(event){
        var obj = this;
        if(event == "click"){
            obj.header.children().bind("click", function(e){ 
                e.preventDefault();
                return obj.calculate();
            })
        }
    },
    calculate: function(){
        var obj = this,  
            header = obj.header,  
            component = obj.component,
            fieldName = obj.fieldName, //I cannot put default value here (e.g. a variable that holds -value or value, because no value will be remembered since we instantiate a new Table object at the end of this function call with initializeTable().)
            msgClass = "msgClass",
            msgList = $(document.createElement("ul")).addClass("msgClass"),  
            types = header.attr("data-sorter").split(" "),
            container = header.parent(), 
            messages = [];
            header.next(".msgClass").remove(); 

            for(var type in types){  
                var criterion = lists.getCriteria(types[type]);
            }
            var result = criterion.insert("order", "page");
            result = result(fieldName, 1);  

            container.addClass("waitingMsg");   
            messages.push(criterion.msg);  

            initializeTable(component, result);
    }
}

$('#dashboard a').click(function(){
    var currentComponent = lists.create(this);
    var defaults = lists.setDefaults(currentComponent);
    initializeTable(defaults);
});

var initializeTable = function(defaults, custom){

    var custom = custom || {};

    var query_string = $.extend(defaults, custom);

    var params = [];
    $.each(query_string, function(key,value){
        params += "&" + key + '=' + value;
    })
    params = params.substring(1);
    var url = params.substring(params.indexOf("=") + 1,params.indexOf("&"));
    params = params.substring(params.indexOf("&")+1, params.length);

    $.ajax({
        type: 'GET',
        url: '/' + url,
        data: params,
        dataType: 'html',
        error: function(){},
        beforeSend: function(){},
        complete: function() {},
        success: function(response) { 
            listview.html(response);

                var form = $('form');
                form.calculation();  

                var table = $('table');
                table.calculation();

        }
    })


}

$.extend($.fn, {   
    calculation: function(){

            switch($(this)[0].nodeName){
                case 'FORM':
                    var formReady = new Form($(this));

                    if(!formReady.isCalculable){
                        return false;  
                    }
                    break;
                case 'TABLE':
                    var tableReady = new Table($(this))
                    if(!tableReady.isSortable){
                        return false;
                    }
                    break;
            }

    }
})

})(jQuery)
</script>

_index.html.erb:

<th data-sorter="sort"><a href="<%= (params[:order].nil?) ? :site_num : params[:order] %>">Site</a></th>

1 个答案:

答案 0 :(得分:0)

这是有问题的功能。

    insert: function(order, page){
        arr = [];
        arr[arr.length] = order;
        arr[arr.length] = page;
        return function(order_value, page_value){  
            var order_value = (order_value.indexOf("-") > -1) ? order_value : "-" + order_value;
            var page_value = page_value;
            return {order : order_value, page : page_value };
        }
    },

你会注意到这一行

var order_value = (order_value.indexOf("-") > -1) ? order_value : "-" + order_value;

正在重新定义order_value(我发现奇怪,不确定是否是原因)可能导致编译器混淆。

由于三元运算符永远不会在order_value中找到符号,因此可能指向order_value是一个整数的事实。

尝试将此行放在上一行之前:

alert((typeof order_value) + " : " + order_value.toString());