var
JSORB =
function
() {};
JSORB.VERSION = '0.04
';
JSORB.AUTHORITY = '
cpan:STEVAN
';
/***************************** JSORB.Client *****************************/
JSORB.Client = function (options) {
if (typeof options == '
string
') {
options = { '
base_url
' : options };
}
this.base_url = options['
base_url
'];
// NOTE:
// Supported options can be found
// here:
// we force a few options for sanity
// such as dataType == json and
// we provide an error and success
// handler, otherwise it is all up
// to you.
// - SL
this.ajax_options = options['
ajax_options
'] || {};
this.base_namespace = options['
base_namespace
'] || null;
this.default_error_handler = options['
default_error_handler
'] || function (e) { alert(e.message) };
this.message_count = 0;
this.__current_xhr = null;
}
JSORB.Client.prototype.new_request = function (p) {
return new JSORB.Client.Request(p);
}
JSORB.Client.prototype.notify = function (request, error_handler) {
request = this.__coerce_request(request);
if (request.id != null) {
throw new Error ("Notifications must have an id of null, you have " + request.id);
}
// notifications do not require
// a callback, so we just pass in
// an empty one here - SL
this.__call(request, function () {}, error_handler);
}
JSORB.Client.prototype.call = function (request, callback, error_handler) {
request = this.__coerce_request(request);
if (request.id == null) {
this.message_count++;
request.id = this.message_count;
}
this.__call(request, callback, error_handler);
}
JSORB.Client.prototype.abort_current_call = function () {
if (this.__current_xhr) {
this.__current_xhr.abort();
this.__current_xhr = null;
}
}
JSORB.Client.prototype.__coerce_request = function (request) {
if (typeof request == '
object
' && request.constructor != JSORB.Client.Request) {
request = this.new_request(request);
}
return request;
}
// NOTE:
// call should take a HASH and that
// hash should be merged into ajax_options
// - SL
JSORB.Client.prototype.__call = function (request, callback, error_handler) {
var self = this;
if (error_handler == undefined) {
error_handler = this.default_error_handler;
}
if (this.base_namespace) {
request.method = this.base_namespace + request.method;
}
// clone our global options
var options = JSORB.Util.clone_object(this.ajax_options);
options.url = request.as_url(this.base_url);
options.dataType = '
text
'; // jQuery keeps not liking my JSON, odd - SL
options.error = function (request, status, error) {
var resp;
if (error) {
// this is for exceptions that happen
// during processing of the AJAX request
// so we can turn this into an actual
// JSORB response with an error for
// the sake of consistency
resp = new JSORB.Client.Response({
'
error
' : new JSORB.Client.Error({
'
error
' : error,
'
message
' : error.description
})
});
}
else {
resp = new JSORB.Client.Response(request.responseText);
}
error_handler(resp.error);
// clear the current xhr
self.__current_xhr = null;
};
options.success = function (data, status) {
var resp = new JSORB.Client.Response(data);
if (request.id != resp.id) {
throw new Error ("Message id mismatch got " + resp.id + " expected " + request.id);
}
if (resp.has_error()) {
error_handler(resp.error);
}
else {
callback(resp.result);
}
// clear the current xhr
self.__current_xhr = null;
};
this.__current_xhr = JSORB.Util.do_ajax_call(options);
}
/*************************** JSORB.Client.Request ****************************/
// Request
JSORB.Client.Request = function (p) {
if (typeof p == '
string
') {
p = JSON.parse(p);
}
// FIXME:
// This should probably check
// for bad input here, and
// throw an exception - SL
this.id = p['
id
'] || null;
this.method = p['
method
'];
this.params = p['
params
'] && typeof p['
params
'] == '
string
'
? JSON.parse(p['
params
'])
: p['
params
'];
}
JSORB.Client.Request.prototype.is_notification = function () { return this.id == null }
JSORB.Client.Request.prototype.as_url = function (base_url) {
var params = [ '
jsonrpc=2.0
' ];
if (this.id != null) {
params.push('
id=
' + escape(this.id));
}
params.push('
method=
' + escape(this.method));
if (this.params) {
params.push('
params=
' + escape(JSON.stringify(this.params)));
}
return (base_url == undefined ? '
' : base_url) + '
?
' + params.join('
&
');
}
JSORB.Client.Request.prototype.collapse_for_json = function () {
return {
'
jsonrpc
' : '
2.0
',
'
id
' : this.id,
'
method
' : this.method,
'
params
' : this.params
};
}
JSORB.Client.Request.prototype.as_json = function () {
return JSON.stringify(this.collapse_for_json());
}
/*************************** JSORB.Client.Response ***************************/
// Response
JSORB.Client.Response = function (p) {
if (typeof p == '
string
') {
p = JSON.parse(p);
}
// FIXME:
// This should probably check
// for bad input here, and
// throw an exception - SL
this.id = p['
id
'];
this.result = p['
result
'];
this.error = p['
error
'] ? new JSORB.Client.Error(p['
error
']) : null;
}
JSORB.Client.Response.prototype.has_error = function () { return this.error != null }
JSORB.Client.Response.prototype.collapse_for_json = function () {
return {
'
id
' : this.id,
'
result
' : this.result,
'
error
' : (this.has_error() ? this.error.collapse_for_json() : null)
};
}
JSORB.Client.Response.prototype.as_json = function () {
return JSON.stringify(this.collapse_for_json());
}
/************************** JSORB.Client.Error **************************/
// Simple error object
JSORB.Client.Error = function (options) {
if (options == undefined) {
options = {};
}
this.code = options['
code
'] || 1;
this.message = options['
message
'] || "An error has occured";
this.data = options['
data
'] || {};
}
JSORB.Client.Error.prototype.collapse_for_json = function () {
return {
'
code
' : this.code,
'
message
' : this.message,
'
data
' : this.data
};
}
JSORB.Client.Error.prototype.as_json = function () {
return JSON.stringify(this.collapse_for_json());
}
/***************************** JSORB.Util ******************************/
JSORB.Util = function () {}
JSORB.Util.clone_object = function (object) {
return jQuery.extend({}, object);
}
JSORB.Util.do_ajax_call = function (options) {
// NOTE:
// This must return the raw
// XMLHTTPRequest object.
// - SL
return jQuery.ajax(options);
}
/***********************************************************************/
/*
DEPENDENCIES
This requires the standard JSON
library, which can be found here:
And a copy of the JQuery library
which can be found here:
BUGS
All complex software has bugs lurking in it, and this module is no
exception. If you find a bug please either email me, or add the bug
to cpan-RT.
AUTHOR
Stevan Little <stevan.little@iinteractive.com>
COPYRIGHT AND LICENSE
Copyright 2008-2010 Infinity Interactive, Inc.
This library is free software; you can redistribute it and/or modify
it under the same terms as Perl itself.
*/
// ****************************************************************************
// ****************************************************************************
//
// [3]_______________________________ \ ___/
// / __/ \ / \__ \
// / / \/ \ \
// / / ___________ \ \
// / / __/___________\__ \ \
// ./ /__ ___ /=================\ ___ __\ \.
// [4]-------> ___||___|====|[[[[[|||||||]]]]]|====|___||___ <------[4]
// / / |=o=o=o=o=o=o=o=o=| <-------------------[5]
// .'
/ \_______ _______/ \ `.