diff options
-rw-r--r-- | jquery.rpc.js | 117 |
1 files changed, 88 insertions, 29 deletions
diff --git a/jquery.rpc.js b/jquery.rpc.js index 9d975ef..397c58f 100644 --- a/jquery.rpc.js +++ b/jquery.rpc.js @@ -1,15 +1,23 @@ - - window.jQuery = window.jQuery || {}; -jQuery.rpc = function(url, dataType, onLoadCallback, version) { +jQuery.rpc = function(url, dataType, onLoadCallback, version, methods) { return new (function(url, dataType, onLoadCallback, version) { version = version || "1.0"; dataType = dataType || "json"; if(dataType != "json" && dataType != "xml") { new Error("IllegalArgument: Unsupported data type"); } + var _self = this; + + function pad2(f) { + if(f<=9) { + return "0"+f; + } else { + return ""+f; + } + } + var serializeToXml = function(data) { switch (typeof data) { case 'boolean': @@ -24,7 +32,7 @@ jQuery.rpc = function(url, dataType, onLoadCallback, version) { return '<string>'+ data +'</string>'; case 'object': if(data instanceof Date) { - return '<dateTime.iso8601>'+ data.getFullYear() + data.getMonth() + data.getDate() +'T'+ data.getHours() +':'+ data.getMinutes() +':'+ data.getSeconds() +'</dateTime.iso8601>'; + return '<dateTime.iso8601>'+ data.getFullYear() + pad2(data.getMonth()) + pad2(data.getDate()) +'T'+ pad2(data.getHours()) +':'+ pad2(data.getMinutes()) +':'+ pad2(data.getSeconds()) +'</dateTime.iso8601>'; } else if(data instanceof Array) { var ret = '<array><data>'+"\n"; for (var i=0; i < data.length; i++) { @@ -52,7 +60,18 @@ jQuery.rpc = function(url, dataType, onLoadCallback, version) { return ret; } var parseXmlValue = function(node) { - childs = jQuery(node).children(); + var jnode = jQuery(node); + childs = jnode.children(); + + // String not enclosed in a <string> tag + if(childs.length==0) { + var s=""; + for(var j=0; j<jnode[0].childNodes.length;j++) { + s+=new String(jnode[0].childNodes[j].nodeValue); + } + return s; + } + for(var i=0; i < childs.length; i++) { switch(childs[i].tagName) { case 'boolean': @@ -81,7 +100,7 @@ jQuery.rpc = function(url, dataType, onLoadCallback, version) { return ret; case "dateTime.iso8601": /* TODO: fill me :( */ - return NULL; + return 0; } } } @@ -104,24 +123,38 @@ jQuery.rpc = function(url, dataType, onLoadCallback, version) { 'xml':'text/xml' ,'json':'application/json' }; - var _rpc = function(method, callback) { + var _rpc = function(method) { var params = []; - for (var i=2; i<arguments.length; i++) { + var async; // whether we're async or not + var callback; + var nargs=arguments.length; + + if(nargs > 1 && typeof(arguments[nargs-1])=="function") { + callback = arguments[nargs-1]; + nargs=nargs-1; + async=true; + } else { + async=false; + } + + for (var i=1; i<nargs; i++) { params.push(arguments[i]); } - // console.log(params); + var data; if(dataType == 'json') { data = {"version":version, "method":method, "params":params}; } else { data = xmlRpc(method, params); } + + if(async) { jQuery.ajax({ - "url": url, - "dataType": dataType, - "type": "POST", - "data": data, - "success": function(inp) { + url: url, + dataType: dataType, + type: "POST", + data: data, + success: function(inp) { var json = inp; if(dataType == "xml") { json = parseXmlResponse(inp); @@ -129,20 +162,31 @@ jQuery.rpc = function(url, dataType, onLoadCallback, version) { // console.log("json response:", json); callback(json); }, - "processData": false, - "contentType": rpc_contents[dataType] - }); + processData: false, + contentType: rpc_contents[dataType]}); + } else { + var result = jQuery.ajax({ + url: url, + dataType: dataType, + type: "POST", + data: data, + async: false, + contentType: rpc_contents[dataType]}); + if(dataType=="json") { + return eval("("+result.responseText+")"); + } else { + var myresult=parseXmlResponse(result.responseXML); + return myresult; + } + } + }; - _rpc("system.listMethods", - function(json) { + function populate(methods) { // console.log(json); /* get the functions */ - if(!json.result) { - return; - } var proc = null; - for(var i = 0; i<json.result.length; i++) { - proc = json.result[i]; + for(var i = 0; i<methods.length; i++) { + proc = methods[i]; var obj = _self; var objStack = proc.split(/\./); for(var j = 0; j < (objStack.length - 1); j++){ @@ -153,24 +197,39 @@ jQuery.rpc = function(url, dataType, onLoadCallback, version) { obj[objStack[j]] = ( function(method, obj) { var _outer = {"method":method,"rpc":_rpc}; - return function(callback) { + return function() { var params = []; params.push(_outer.method); - params.push(callback); - for (var i=1; i<arguments.length; i++) { + for (var i=0; i<arguments.length; i++) { params.push(arguments[i]); } - _rpc.apply(_self, params); + return _rpc.apply(_self, params); } } )(proc, _rpc); } // console.log('Load was performed.'); + } + + function asyncCallback(json) { + populate(json.result); if(onLoadCallback) { onLoadCallback(_self); } } - ); + + if(!methods) { + _rpc("system.listMethods", asyncCallback); + } else { + populate(methods); + if(onLoadCallback) { + // not sure this works - the intention is to call the callback as soon as this + // javascript function returns control back to the browser, to emulate the behaviour + // that the system.listMethods approach + setTimeout(function(){onLoadCallback(_self);},0); + } + } + })(url, dataType, onLoadCallback, version); }; |