var EdconfRequestCount = 0;

var EdconfRequest = Class.create({
	rootUrl: '/cgi-bin/public/edconfd.cgi',
	initialize: function(inOptions) {
		this.options = {
			methodName: '',
			callback: null,
			parameters: {},
			postData: null,
			expectXml: true,
			on403: null,
			on404: null,
			on500: null,
			noLoadingMessage: false,
			infoText: null
		};
		this.ajaxparams = {};
		
		this.parseOptions(inOptions);
	},
	parseOptions: function(inOptions) {
		Object.extend(this.options, inOptions || {});
		
		this.sendRequest();
	},
	sendRequest: function() {
		this.ajaxparams = {
			encoding: 'iso-8859-1',
			method: this.options.method,
			parameters: this.options.parameters,
			onSuccess: this.onSuccess.bind(this),
			onFailure: this.options.onError,
			onException: this.onException.bind(this),
			on500: this.on500.bind(this),
			on404: this.on404.bind(this),
			on403: this.on403.bind(this),
			on412: this.on412.bind(this),
			method: 'get'
		};
		
		// Make sure onError catches all the errors
		if(this.options.onError) {
			this.ajaxparams.on500 = null;
			this.ajaxparams.on404 = null;
			this.ajaxparams.on403 = null;
			this.ajaxparams.on412 = null;
		} else {
			this.ajaxparams.onFailure = this.options.onError = this.onError.bind(this);
		}
		
		if(this.options.postData || 'post' == this.options.method) {
			if(this.options.postData instanceof XmlBuffer) {
				// For debugging purposes
				this.ajaxparams.postBody = this.options.postData.getXml();
				debug(this.options.postData.inspect());
			} else {
				this.ajaxparams.postBody = this.options.postData;
			}
			this.ajaxparams.method = 'post';
		} else {
			// Add a date stamp to make sure the request doesn't get cached
			this.ajaxparams.parameters.ts = (new Date()).getTime();
		}
		
		if(!this.options.noLoadingMessage) this.showLoadingMessage();
		
		new Ajax.Request(this.rootUrl +'?method='+ this.options.methodName, this.ajaxparams);
	},
	onSuccess: function(inResponse) {
		if(!this.options.noLoadingMessage) this.hideLoadingMessage();
		if(this.options.expectXml
			&& (!inResponse.responseXML || !inResponse.responseXML.documentElement)) {
			return this.options.onError(inResponse);
		}
		if(!this.options.callback) return;
		if(this.options.expectXml) {
			return this.options.callback(new XmlData(inResponse.responseXML.documentElement));
		} else {
			return this.options.callback();
		}
	},
	onError: function(inResponse, inForwarded) {
		// 0 should mean no network or dropped request
		// ie when changing page while a request is being sent
		if(!this.options.noLoadingMessage && !inForwarded) this.hideLoadingMessage();
		if(0 != inResponse.status) {
			setStatus('error', getTranslation('id24'));
		}
		debug('[EdconfRequest] Error '+ inResponse.status +' on request: '+ inResponse.request.url);
	},
	onException: function(inRequest, inException) {
		var myMessage = '[EdconfRequest] Exception';
		
		if(!this.options.noLoadingMessage) this.hideLoadingMessage();
		
		if(inException.fileName && inException.lineNumber) {
			var myFileName = inException.fileName.split('/');
			
			myFileName = myFileName[myFileName.length-1];
			myMessage += ' ('+ myFileName +'@'+ inException.lineNumber +')';
		}
		if(inException.message) myMessage += ': '+ inException.message;
		
		// setStatus('error', getTranslation('id24'));
		debug(myMessage);
		edconfd_down = true;
	},
	on500: function(inResponse) {
		if(!this.options.noLoadingMessage) this.hideLoadingMessage();
		if(this.options.on500) this.options.on500(inResponse);
		else this.onError(inResponse, true);
	},
	on404: function(inResponse) {
		if(!this.options.noLoadingMessage) this.hideLoadingMessage();
		if(this.options.on404) this.options.on404(inResponse);
		else this.onError(inResponse, true);
	},
	on403: function(inResponse) {
		if(!this.options.noLoadingMessage) this.hideLoadingMessage();
		if(this.options.on403) this.options.on403(inResponse);
		else window.location = '/login.html';
	},
	on412: function(inResponse) {
		if(!this.options.noLoadingMessage) this.hideLoadingMessage();
		if(this.options.on412) this.options.on412(inResponse);
		else this.onError(inResponse, true);
	},
	showLoadingMessage: function() {
		EdconfRequestCount++;
		if(this.options.infoText) setStatus('loading', this.options.infoText);
		else setStatus('loading', getTranslation('id12'));
	},
	hideLoadingMessage: function() {
		EdconfRequestCount--;
		if(!EdconfRequestCount) setStatus('clear');
	}
});

var DownloadRequest = Class.create(EdconfRequest, {
	rootUrl: '/api/download',
	initialize: function($super, inOptions) {
		$super(inOptions);
	}
});

var BackupRequest = Class.create(EdconfRequest, {
	rootUrl: '/api/backup',
	initialize: function($super, inOptions) {
		$super(inOptions);
	}
});
