//---- TSPField ----
function TSPField(aValue)
{
	this.Value = aValue;
}

//---- TSPRecord ----
function TSPRecord()
{
	this.FieldCount = 0;
	this.Field = new Array;
	this.Add = TSPRecord_AddField;
	this.Name = TSPRecord_GetName;
}

function TSPRecord_AddField(aName)
{
	this.Field[this.FieldCount] = new TSPField(aName);
	this.FieldCount++;
}

function TSPRecord_GetName(aIndex)
{
	if(aIndex < this.FieldCount)
	{
		return this.Field[aIndex].Value;
	}
	return null;
}

//---- TSPDataset ----
function TSPDataset()
{
	this.RecNo = 0;
	this.Columns = new TSPRecord();
	this.RecordCount = 0;
	this.Record = new Array;
	this.RowDelimiter = "\n";
	this.ColumnDelimiter = "|";
	this.eof = true;
	this.AJAXCallback = null;
	this.ColumnCount = TSPDataset_GetColumnCount;
	this.ColumnName = TSPDataset_GetColumnName; 
	this.First = TSPDataset_First;
	this.Last = TSPDataset_Last;
	this.Next = TSPDataset_Next;
	this.Prior = TSPDataset_Prior;
	this.Append = TSPDataset_Append;
	this.Fields = TSPDataset_Fields;
	this.FieldByName = TSPDataset_FieldByName;
	this.Locate = TSPDataset_Locate;
	this.LoadData = TSPDataset_LoadData;
	this.SaveData = TSPDataset_SaveData;
	this.Clear = TSPDataset_Clear;
	this.LoadCSV = TSPDataset_LoadCSV;
	this.SaveCSV = TSPDataset_SaveCSV;
	this.LoadXML = TSPDataset_LoadXML;
	this.SaveXML = TSPDataset_SaveXML;
	this.LoadAJAX = TSPDataset_LoadAJAX;
}

function TSPDataset_GetColumnCount()
{
	return this.Columns.FieldCount;
}

function TSPDataset_GetColumnName(aIndex)
{
	return this.Columns.Name(aIndex);
}

function TSPDataset_Locate(aFieldName, aValue)
{
	var LFieldIndex = -1;
	for(var i = 0; i < this.Columns.FieldCount; i++)
	{
		if(this.Columns.Name(i) == aFieldName)
		{
			LFieldIndex = i;
			break;
		}
	}

	if(LFieldIndex != -1)
	{
		this.First();
		while(!this.eof)
		{
			if(this.FieldByName(aFieldName).Value == aValue)
			{
				return true;
			}
			this.Next()
		}
	}
	return false;
}

function TSPDataset_First()
{
	this.eof = (this.RecordCount == 0);
	this.RecNo = 0;
}

function TSPDataset_Last()
{
	this.eof = true;
	this.RecNo = this.RecordCount - 1;
}

function TSPDataset_Next()
{
	if(this.RecNo < this.RecordCount - 1)
	{
		this.RecNo = this.RecNo + 1;
	}
	else
	{
		this.eof = true;
	}
}

function TSPDataset_Prior()
{
	if(this.RecNo > 0)
	{
		this.RecNo = this.RecNo - 1;
		this.eof = false;
	}
}

function TSPDataset_Append()
{
	this.Record[this.RecordCount] = new TSPRecord();
	for(var i = 0; i < this.Columns.FieldCount; i++)
	{
		this.Record[this.RecordCount].Add("");
	}
	this.RecNo = this.RecordCount; 
	this.RecordCount++;
	this.eof = true;
}

function TSPDataset_Fields(aFieldIndex)
{
	if(aFieldIndex < this.ColumnCount())
	{
		return this.Record[this.RecNo].Field[aFieldIndex];
	}
	
	return null;
}

function TSPDataset_FieldByName(aFieldName)
{
	var LFieldIndex = -1;
	for(var i = 0; i < this.Columns.FieldCount; i++)
	{
		if(this.Columns.Name(i) == aFieldName)
		{
			LFieldIndex = i;
			break;
		}
	}

	if(LFieldIndex != -1)
	{
		return this.Fields(LFieldIndex);
	}

	return null;
}

function TSPDataset_LoadData(aDataStr)
{
	this.RecNo = 0;
	this.RecordCount = 0;
	this.eof = true;
	var Record = null;
	var Field = null;
	var i;
	var j;
	if(aDataStr != "")
	{
		var Record = aDataStr.split(this.RowDelimiter);
		for(i = 0; i < Record.length; i++)
		{	
			Field = Record[i].split(this.ColumnDelimiter);
			if(Field.length > 0)
			{	
				this.Append();
				for(j = 0; (j < Field.length) && (j < this.ColumnCount()); j++)
				{
					this.Fields(j).Value = Field[j];
				}
			}
		}
	}
}

function TSPDataset_SaveData()
{
	var LDataStr = "";
	var LRowStr = "";
	var LRecNo = this.RecNo;
	this.First();
	while(!this.eof)
	{
		LRowStr = "";
		for(i = 0; i < this.ColumnCount(); i++)
		{
			if (LRowStr != "")
			{
				LRowStr += this.ColumnDelimiter;
			}
			LRowStr += this.Fields(i).Value;
		}

		if (LDataStr != "")
		{
			LDataStr += this.RowDelimiter; 
		}
		
		LDataStr += LRowStr;
		
		this.Next();
	}
	this.RecNo = LRecNo;

	return LDataStr;
}

function TSPDataset_Clear()
{
	this.RecordCount = 0;
	this.RecNo = 0;
	this.eof = true;
}

function TSPDataset_LoadCSV(csvdata, includeHeader)
{
	this.Clear();
	var record = null;
	var field = null;
	var i;
	var j;
	if(csvdata != "")
	{
		record = csvdata.split(this.RowDelimiter);
		for(i = 0; i < record.length; i++)
		{
			field = record[i].split(this.ColumnDelimiter);
			if(field.length > 0)
			{	
				if(i == 0 && includeHeader)
				{
					this.Columns = new TSPRecord();
					for(j = 0; j < field.length; j++)
					{
						this.Columns.Add(field[j]);
					}
				}
				else
				{
					this.Append();
					for(j = 0; (j < field.length) && (j < this.ColumnCount()); j++)
					{
						this.Fields(j).Value = field[j];
					}
				}
			}
		}
	}
}

function TSPDataset_SaveCSV()
{
	var csvdata = "";
	var rowStr = "";
	var recNo = this.RecNo;
	this.First();
	while(!this.eof)
	{
		rowStr = "";
		for(i = 0; i < this.ColumnCount(); i++)
		{
			if (rowStr != "")
			{
				rowStr += this.ColumnDelimiter;
			}
			rowStr += this.Fields(i).Value;
		}

		if (csvdata != "")
		{
			csvdata += this.RowDelimiter; 
		}
		
		csvdata += rowStr;
		
		this.Next();
	}
	this.RecNo = recNo;

	return csvdata;
}

function TSPDataset_LoadXML(xmldata)
{
	this.Clear();
	var xmlDoc = null;
	try 
	{
		//Internet Explorer
		xmlDoc = new ActiveXObject("Microsoft.XMLDOM");
		xmlDoc.async = "false";
		xmlDoc.loadXML(xmldata);
	}
	catch(e)
	{
		try 
		{
			//Firefox, Mozilla, Opera, etc.
			parser = new DOMParser();
			xmlDoc = parser.parseFromString(xmldata, "text/xml");
		}
		catch(e)
		{
			alert(e.message);
			return;
		}
	}

	// Parse data
	var dataNode = null;
	var rowNode = null;
	var columnNode = null;
	for(var i = 0; i < xmlDoc.childNodes.length; i++)
	{
		if(xmlDoc.childNodes[i].nodeName != "xml")
		{
			dataNode = xmlDoc.childNodes[i];
			break;
		}
	}

	if(dataNode != null)
	{
		// column
		if(dataNode.childNodes.length > 0)
		{
			rowNode = dataNode.childNodes[0];
			for(var index = 0; index < rowNode.childNodes.length; index++)
			{
				columnNode = rowNode.childNodes[index];
				this.Columns.Add(columnNode.nodeName);
			}
		}

		// data
		for(var j = 0; j < dataNode.childNodes.length; j++)
		{
			rowNode = dataNode.childNodes[j];
			if(rowNode != null)
			{
				this.Append();
				for(var index = 0; index < this.ColumnCount(); index++)
				{
					columnNode = rowNode.getElementsByTagName(this.ColumnName(index).toLowerCase())[0];
					if(columnNode != null)
					{
						this.Fields(index).Value = columnNode.childNodes[0].nodeValue;
					}
				}
			}
		}
	}
}

function TSPDataset_SaveXML(tablename)
{
	var xmldata = "<?xml version=\"1.0\"?>\n";
	xmldata += "<" + tablename + "s>\n";
	var recNo = this.RecNo;
	this.First();
	while(!this.eof)
	{
		xmldata += "\t<" + tablename + ">\n";
		for(i = 0; i < this.ColumnCount(); i++)
		{
			xmldata += "\t\t<" + this.ColumnName(i) + ">" + this.Fields(i).Value + "</" + this.ColumnName(i) + ">\n";
		}
		xmldata += "\t</" + tablename + ">\n"
		
		this.Next();
	}
	xmldata += "</" + tablename + "s>\n";
	this.RecNo = recNo;

	return xmldata;
}

function TSPDataset_LoadAJAX(url, data)
{
	// initialise xml request
	var xmlHttp = null;
	try
	{
		// Firefox, Opera 8.0+, Safari
		xmlHttp = new XMLHttpRequest();
	}
	catch (e)
	{
		// Internet Explorer
		try
		{
			xmlHttp = new ActiveXObject("Msxml2.XMLHTTP");
		}
		catch (e)
		{
			xmlHttp = new ActiveXObject("Microsoft.XMLHTTP");
		}
	}

	if(xmlHttp == null)
	{
		alert("Your browser does not support AJAX!");
	}
	else
	{
		oThis = this;
		xmlHttp.onreadystatechange = function()
		{
			if(xmlHttp.readyState == 4)
			{
				if(xmlHttp.responseText != "")
				{
					oThis.LoadCSV(xmlHttp.responseText, true);
				}
				if(oThis.AJAXCallback != null)
				{
					oThis.AJAXCallback();
				}
			}
		};

		if(data == null)
		{
			xmlHttp.open("GET", url, true, null, null);
			//xmlHttp.setRequestHeader("Connection", "Keep-Alive");
			xmlHttp.send(null);
		}
		else
		{
			data = data.replace(/ /gi, "+");
			data = data.replace(/\n/gi, "+");
			xmlHttp.open("POST", url, true);
			xmlHttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
			//xmlHttp.setRequestHeader("Content-length", data.length);
			//xmlHttp.setRequestHeader("Connection", "Keep-Alive");
			xmlHttp.send(data);
		}
	}
}