Thursday, 3 June 2010

C#: Xml to Array Serializer

This is a simple code that I wrote to serialize Xml.

@XmlSerializer: all the business logic to serialize
@Array: resulting wrapped up string as an array abstraction that becomes handy.
@EmptyArray
@IArrayItem, @ArrayItem: Values inserted in an of the array
@ArrayCharacter: String characters that construct an array

@XmlSerializer:

public class XmlToArraySerializer : ISerializer
{
public string Serialize(XElement xml)
{
return ConvertXElementToArray(xml).ToString();
}

private ArrayItem ConvertXElementToArray(XElement element)
{
Array array = new Array();

array.Start();
array.Insert(SerializeAttributes(element));

if (element.HasElements)
{
array.Insert(SerializeChildElements(element));
}
else
{
array.Insert(SerializeValue(element));
}

array.End();

return new ArrayItem(array);
}

private ArrayItem SerializeChildElements(XElement element)
{
Array array = new Array();
IEnumerable elements = element.Elements();

array.Start();

foreach (XElement childElement in elements)
{
array.Insert(ConvertXElementToArray(childElement));
}

array.End();
return new ArrayItem(array);
}

private ArrayItem SerializeValue(XElement element)
{
if(string.IsNullOrEmpty(element.Value)) return null;

Array array = new Array();

array.Start();
array.Insert(new ArrayItem(element.Value));
array.End();

return new ArrayItem(array);
}

private IArrayItem[] SerializeAttributes(XElement element)
{
IEnumerable attributes = element.Attributes();

IArrayItem[] values = new ArrayItem[attributes.Count()];

int index = 0;

foreach (XAttribute attribute in attributes)
{
values[index++] = new ArrayItem(attribute.Value);
}

return values;
}
}

@Array

public class Array
{
private StringBuilder _array;
private bool _canPutSeperator;

public Array()
{
_array = new StringBuilder();
}

public void Start()
{
InsertArrayCharacter(ArrayCharacter.Start);

_canPutSeperator = false;
}

public void End()
{
InsertArrayCharacter(ArrayCharacter.End);

_canPutSeperator = false;
}

public void InsertEmptyItem()
{
if(_canPutSeperator)
{
InsertArrayCharacter(ArrayCharacter.Seperator);
}

_canPutSeperator = true;
}

public void Insert(IArrayItem arrayItem)
{
if(null == arrayItem) return;

if(arrayItem.IsEmtpy())
{
InsertEmptyItem();
return;
}

EnterNewItem();

_array.Append(arrayItem);

ExitNewItem();
}

public void Insert(IArrayItem[] arrayItems)
{
foreach (IArrayItem item in arrayItems)
{
Insert(item);
}
}

public string EmptyValue()
{
return string.Format("{0}{1}", ArrayCharacter.Start.Value, ArrayCharacter.End.Value);
}

public override string ToString()
{
return !string.IsNullOrEmpty(_array.ToString()) ? _array.ToString() : EmptyValue();
}

public override int GetHashCode()
{
return _array.GetHashCode();
}

public bool IsEmpty()
{
return string.IsNullOrEmpty(_array.ToString());
}

private void EnterNewItem()
{
if (_canPutSeperator)
{
InsertArrayCharacter(ArrayCharacter.Seperator);
}
}

private void ExitNewItem()
{
_canPutSeperator = true;
}

private void InsertArrayCharacter(ArrayCharacter arrayCharacter)
{
_array.Append(arrayCharacter.Value);
}
}

@EmptyArray:

public class EmptyArray
{
public override string ToString()
{
Array emptyArray = new Array();

emptyArray.Start();
emptyArray.End();

return emptyArray.ToString();
}
}

@ArrayItem:

public class ArrayItem : IArrayItem
{
private T _value;

public ArrayItem(T value)
{
_value = value;
}

public bool IsArray()
{
return typeof(T).Equals(typeof(Array)) || typeof(T).Equals(typeof(EmptyArray));
}

public bool IsValue()
{
return typeof (T).Equals(typeof (string))
|| typeof (T).IsPrimitive
|| typeof (T).Equals(typeof (DateTime))
|| typeof (T).Equals(typeof (DateTime?));
}

public bool IsEmtpy()
{
if(null == _value) return true;
if(!IsArray() && !IsValue()) return true;

return IsArray() ? (_value as Array).IsEmpty() : string.IsNullOrEmpty(_value.ToString());
}

private bool NeedsToBeWrappedInQuotes()
{
return !IsArray() && !IsNumeric();
}

private bool IsNumeric()
{
double value;
return double.TryParse(_value.ToString(), out value);
}

public override string ToString()
{
return NeedsToBeWrappedInQuotes() ?
ArrayCharacter.Quote.Value + _value.ToString() + ArrayCharacter.Quote.Value
: _value.ToString();
}

public override int GetHashCode()
{
return _value.GetHashCode();
}
}

public interface IArrayItem
{
bool IsArray();
bool IsValue();
bool IsEmtpy();
}

@ArrayCharacter
public class ArrayCharacter
{
private char _value;

public ArrayCharacter(char value)
{
_value = value;
}

public char Value
{
get { return _value; }
}

public static ArrayCharacter Start = new ArrayCharacter('[');
public static ArrayCharacter End = new ArrayCharacter(']');
public static ArrayCharacter Seperator = new ArrayCharacter(',');
public static ArrayCharacter Quote = new ArrayCharacter('\'');
}

No comments:

Post a Comment