﻿(function($) {
	//	---------------------------------------------------------
	//	             [jQuery.ajaxDotNet, ver 2.0.1]
	//	Copyright (c) 2008 Richard Kimber, http://www.dogma.co.uk
	//	Licensed under the terms of the MIT Licence (LICENSE.txt)
	//	---------------------------------------------------------
	//	On a personal note, I would love to hear about any
	//	implementations of this plugin. richard at dogma.co.uk
	//	---------------------------------------------------------

	function getXhr() {
		if (typeof XMLHttpRequest != "undefined") {
			return new XMLHttpRequest();
		}
		else if (typeof ActiveXObject != "undefined") {
			try {
				return new ActiveXObject('Msxml2.XMLHTTP');
			}
			catch (err) {
				try { return new ActiveXObject('Microsoft.XMLHTTP'); } catch (e) { }
			}
		}
	};

	function cTD(v) {
		var rx = /\/Date\((-?[0-9]+)(\+[0-9]+)?\)\//g;
		if (rx.test(v)) {
			var milli = Number(v.replace(rx, '$1'));
			if (!isNaN(milli))
				v = new Date(Number(v.replace(rx, '$1')));
			else
				throw new Error("Date format not recognised.");
		}
		return v;
	};

	function tO(v) {
		if (v.constructor == String) {
			v = cTD(v);
		}
		else if (v != null && (v.constructor == Object || v.constructor == Array)) {
			$.each(v, function(i, x) {
				v[i] = i != "__type" ? tO(x) : x;
			});
		}
		return v;
	};

	$.ajaxDotNet = function(url, options) {
		options = $.extend({}, $.ajaxDotNet.defaults, options);

		var xhr = getXhr();

		var data = '';
		if (options.verb == 'GET') {
			for (var i in options.data) {
				if (data != '') {
					data += '&';
				}
				data += i + '=' + JSON.stringify(options.data[i]);
			}
			url += '?' + data;
			data = null;
		}
		else if (options.verb == 'POST') {
			data = JSON.stringify(options.data);
		}

		xhr.open(options.verb, url, true); //true = async
		xhr.onreadystatechange = function() {
			if (xhr.readyState == 4) {
				var r = xhr.responseText;
				if (r.constructor == String) {
					if (r != '') {
						try {
							r = JSON.parse(xhr.responseText);
							r = tO(r);
						}
						catch (err) {
							r = err;
						}
					}
					else {
						r = {};
					}
				}

				if (xhr.status == 200 && options.success !== undefined)
					options.success(r, xhr.status, xhr.statusText);
				else if (options.other !== undefined)
					options.other(r, xhr.status, xhr.statusText);
			}
		};
		xhr.setRequestHeader("Content-Type", "application/json; charset=utf-8");
		xhr.send(data);
	};

	$.ajaxDotNet.defaults = {
		verb: 'POST',
		data: new Object(),
		success: function() { },
		other: function() { }
	};
})(jQuery);