self.fwkHttpTransfer = FindProperty('fwkHttpTransfer');

if (IsInvalid(self.fwkHttpTransfer))
{
    //Response
	function HttpResponse(objXmlHttp, req, exception) 
	{
	
		this.request = DefaultIfInvalid(req, null);
		this.exception = DefaultIfInvalid(exception, null);
		if (IsValid(exception))
		{
				this.responseXML = null;
				this.responseText = null;
				this.responseBody = null;
				this.responseStream = null;
				this.status = null;
				this.statusText = null;
				return this;
		}		
		this.responseXML = objXmlHttp.responseXML;
		this.responseText = objXmlHttp.responseText;
		this.responseBody = objXmlHttp.responseBody;
		this.responseStream = objXmlHttp.responseStream;
		this.status = objXmlHttp.status;
		this.statusText = objXmlHttp.statusText;
	}

	//Request
	function HttpRequest(strMethod, url, user, pass, headers, data, boolAsync)
	{
		this.method = strMethod;
		this.url = url;
		this.user = user;
		this.password = pass;
		this.headers = headers;
		this.data = data;
		this.async = boolAsync;
	}

	function XmlHttpWrapper(index, controller) 
	{
		this.callback = null;
		this.xmlHttp = new ActiveXObject("Microsoft.XmlHttp");
		this.index = index;
		this.controller = controller;
	}

	XmlHttpWrapper.prototype.request = 
	function(strMethod, url, user, pass, headers, data, callback, boolAsync) 
	{
		this.callback = null;
		try
		{
			this.xmlHttp.open(strMethod, url, boolAsync, user, pass);
		}
		catch(e)
		{
			return new HttpResponse(null, null, e)
		}
		if (headers!=null && headers!='') {
			var vHeaders = headers.split('&');
			for(var i=0;i<vHeaders.length; i++) {
				vHeader = vHeaders[i].split('=');
				this.xmlHttp.setRequestHeader(vHeader[0], vHeader[1]);
			}
		}

		var request	= new HttpRequest(strMethod, url, user, pass, headers, data, boolAsync);
		if (boolAsync) {
			var self = this;
			this.callback = callback;
			this.xmlHttp.onreadystatechange = function() {
				if (self.xmlHttp.readyState == 4) {
					//wndLog.document.writeln("Response received for " + url + " status:" + self.xmlHttp.status +  "<br>");
					if (self.callback != null)
						self.callback(new HttpResponse(self.xmlHttp, request));
					self.controller.pushFree(self);
				}
				
			}
			try
			{
				this.xmlHttp.send(data);
			}
			catch(e)
			{
				return new HttpResponse(null, null, e)
			}
			
		}
		else {
			try
			{
				this.xmlHttp.send(data);
			}
			catch(e)
			{
				return new HttpResponse(null, null, e)
			}
			//wndLog.document.writeln("Response received for " + url + " status:" + this.xmlHttp.status  + "<br>");
			this.controller.pushFree(this);
			return new HttpResponse(this.xmlHttp, request);
		}
	}

	XmlHttpWrapper.prototype.onreadystatechange = 
	function() 
	{
		if (this.xmlHttp.readyState == 4) {
			//wndLog.document.writeln("Response received for ? status:" + this.xmlHttp.status +  "<br>");
			if (this.callback != null)
				this.callback(new HttpResponse(this.xmlHttp));
			this.controller.pushFree(this);
		}
	}

    //Helper para transfer con AJAX
	var fwkHttpTransfer =
	{
		XmlHttps: [],
		XmlHttpsFree: [],
		MissingComponents: [],
		
		formPostHeader: "Content-Type=application/x-www-form-urlencoded",
		
		EscapeValue: function(strValue)
		{
			var replacer = [[/\x25/g,'%25'],[/\x3B/g,'%3B'],[/\x2F/g,'%2F'],[/\x3F/g,'%3F'],[/\x3A/g,'%3A'],[/\x40/g,'%40'],[/\x26/g,'%26'],[/\x3D/g,'%3D'],[/\x2B/g,'%2B'],[/\x24/g,'%24'],[/\x2C/g,'%2C'],[/\x2D/g,'%2D'],[/\x5F/g,'%5F'],[/\x2E/g,'%2E'],[/\x21/g,'%21'],[/\x7E/g,'%7E'],[/\x2A/g,'%2A'],[/\x27/g,'%27'],[/\x28/g,'%28'],[/\x29/g,'%29'],[/\x20/g,'%20'],[/\x3C/g,'%3C'],[/\x3E/g,'%3E'],[/\x23/g,'%23'],[/\x22/g,'%22'],[/\x7B/g,'%7B'],[/\x7D/g,'%7D'],[/\x7C/g,'%7C'],[/\x5C/g,'%5C'],[/\x5E/g,'%5E'],[/\x5B/g,'%5B'],[/\x5D/g,'%5D'],[/\x60/g,'%60'],[/\x00/g,'%0'],[/\x01/g,'%1'],[/\x02/g,'%2'],[/\x03/g,'%3'],[/\x04/g,'%4'],[/\x05/g,'%5'],[/\x06/g,'%6'],[/\x07/g,'%7'],[/\x08/g,'%8'],[/\x09/g,'%9'],[/\x0A/g,'%A'],[/\x0B/g,'%B'],[/\x0C/g,'%C'],[/\x0D/g,'%D'],[/\x0E/g,'%E'],[/\x0F/g,'%F'],[/\x10/g,'%10'],[/\x11/g,'%11'],[/\x12/g,'%12'],[/\x13/g,'%13'],[/\x14/g,'%14'],[/\x15/g,'%15'],[/\x16/g,'%16'],[/\x17/g,'%17'],[/\x18/g,'%18'],[/\x19/g,'%19'],[/\x1A/g,'%1A'],[/\x1B/g,'%1B'],[/\x1C/g,'%1C'],[/\x1D/g,'%1D'],[/\x1E/g,'%1E'],[/\x7F/g,'%7F']];

			var result = strValue;
			for(var i=0;i<replacer.length;i++)
				result = result.replace(replacer[i][0], replacer[i][1])
				
			return result
		},

		EncodeQueryStringValue: function(strValue)
		{
			return this.EscapeValue(strValue);
		},
		
		escapeValue: function(strValue)
		{
			return this.EscapeValue(strValue);
		},
		
		EncodeFormValue: function(value)
		{
			return value.replace(/&/g, '%26');
		},
		
		getWrapper: function(index) 
		{
			return this.XmlHttps[index];
		},
		
		pushFree: function(wrapper) 
		{
			this.XmlHttpsFree.push(wrapper.index);
		},
		
		getFreeXmlHttps: function() 
		{
			var free, xmlHttp;
			if (this.XmlHttpsFree.length==0) {
				this.XmlHttps[this.XmlHttps.length] = new XmlHttpWrapper(this.XmlHttps.length, this);
				free = this.XmlHttps.length - 1;
			}
			else 
				free = this.XmlHttpsFree.pop();
				
			return this.XmlHttps[free];
		},
		
		Request: function(strMethod, url, data, headers, user, pass)
		{
			return this.doRequest(strMethod, url, user, pass, headers, data, null, false)
		},
		
		AsyncRequest: function(strMethod, url, data, callback, headers, user, pass)
		{
			return this.doRequest(strMethod, url, user, pass, headers, data, callback, true)
		},
		
		doRequest: function(strMethod, url, user, pass, headers, data, callback, async)
		{
			var strData ='';
			var wrapper = this.getFreeXmlHttps();
			return wrapper.request(strMethod, url, user, pass, headers, strData, callback, async)
		}
	}
}

try
{
	new ActiveXObject("Microsoft.XmlHttp");
}
catch(e)
{
	fwkHttpTransfer.MissingComponents.push("Microsoft.XmlHttp");
}
