PageRenderTime 29ms CodeModel.GetById 19ms RepoModel.GetById 0ms app.codeStats 1ms

/Xpand/Xpand.ExpressApp.Modules/IO/Core/ExportEngine.cs

https://github.com/krazana/eXpand
C# | 148 lines | 132 code | 16 blank | 0 comment | 20 complexity | 3d881c936ea49033699a9344ecd21c5c MD5 | raw file
  1. using System;
  2. using System.Collections;
  3. using System.Collections.Generic;
  4. using System.Globalization;
  5. using System.IO;
  6. using System.Xml;
  7. using System.Xml.Linq;
  8. using DevExpress.Xpo;
  9. using DevExpress.Xpo.Metadata;
  10. using System.Linq;
  11. using Xpand.Persistent.Base.ImportExport;
  12. using Xpand.Utils.Helpers;
  13. namespace Xpand.ExpressApp.IO.Core {
  14. public class ExportEngine {
  15. readonly Dictionary<ObjectInfo, object> exportedObjecs = new Dictionary<ObjectInfo, object>();
  16. SerializeClassInfoGraphNodesCalculator _serializeClassInfoGraphNodesCalculator ;
  17. public XDocument Export(IEnumerable<XPBaseObject> baseCollection, ISerializationConfigurationGroup serializationConfigurationGroup){
  18. var xDocument = new XDocument();
  19. var root = new XElement("SerializedObjects");
  20. xDocument.Add(root);
  21. _serializeClassInfoGraphNodesCalculator =new SerializeClassInfoGraphNodesCalculator(serializationConfigurationGroup);
  22. foreach (var baseObject in baseCollection) {
  23. IEnumerable<IClassInfoGraphNode> serializedClassInfoGraphNodes =
  24. _serializeClassInfoGraphNodesCalculator.GetSerializedClassInfoGraphNodes(baseObject);
  25. ExportCore(baseObject, serializedClassInfoGraphNodes, root);
  26. }
  27. return xDocument;
  28. }
  29. void ExportCore(XPBaseObject selectedObject, IEnumerable<IClassInfoGraphNode> serializedClassInfoGraphNodes, XElement root) {
  30. var objectInfo = new ObjectInfo(selectedObject.GetType(),selectedObject.ClassInfo.KeyProperty.GetValue(selectedObject));
  31. if (!(exportedObjecs.ContainsKey(objectInfo))){
  32. exportedObjecs.Add(objectInfo, null);
  33. var serializedObjectElement = new XElement("SerializedObject");
  34. serializedObjectElement.Add(new XAttribute("type", selectedObject.GetType().Name));
  35. root.Add(serializedObjectElement);
  36. foreach (var classInfoGraphNode in serializedClassInfoGraphNodes.Where(node => node.SerializationStrategy!=SerializationStrategy.DoNotSerialize)) {
  37. XElement propertyElement = GetPropertyElement(serializedObjectElement, classInfoGraphNode);
  38. switch (classInfoGraphNode.NodeType) {
  39. case NodeType.Simple:
  40. SetMemberValue(selectedObject, classInfoGraphNode, propertyElement);
  41. break;
  42. case NodeType.Object:
  43. CreateObjectProperty(selectedObject, propertyElement, classInfoGraphNode, root);
  44. break;
  45. case NodeType.Collection:
  46. CreateCollectionProperty(selectedObject, classInfoGraphNode, root, propertyElement);
  47. break;
  48. }
  49. }
  50. }
  51. }
  52. void SetMemberValue(XPBaseObject selectedObject, IClassInfoGraphNode classInfoGraphNode, XElement propertyElement) {
  53. var xpMemberInfo = selectedObject.ClassInfo.FindMember(classInfoGraphNode.Name);
  54. if (xpMemberInfo != null ) {
  55. var memberValue = selectedObject.GetMemberValue(classInfoGraphNode.Name);
  56. if (xpMemberInfo.Converter != null)
  57. memberValue = (xpMemberInfo.Converter.ConvertToStorageType(memberValue));
  58. if (memberValue is byte[])
  59. memberValue = Convert.ToBase64String((byte[])memberValue);
  60. if (memberValue is DateTime)
  61. memberValue = ((DateTime)memberValue).Ticks;
  62. if (memberValue is string)
  63. propertyElement.Add(new XCData(memberValue.ToString()));
  64. else {
  65. propertyElement.Value = GetInvariantValue(memberValue);
  66. }
  67. }
  68. }
  69. string GetInvariantValue(object memberValue) {
  70. double result;
  71. var parse = Double.TryParse(memberValue+"",out result);
  72. return parse ? ((IConvertible) memberValue).ToString(CultureInfo.InvariantCulture) : memberValue + "";
  73. }
  74. XElement GetPropertyElement(XElement serializedObjectElement, IClassInfoGraphNode classInfoGraphNode) {
  75. var propertyElement = new XElement("Property");
  76. serializedObjectElement.Add(propertyElement);
  77. propertyElement.Add(new XAttribute("type", classInfoGraphNode.NodeType.ToString().MakeFirstCharLower()));
  78. propertyElement.Add(new XAttribute("name", classInfoGraphNode.Name));
  79. propertyElement.Add(new XAttribute("isKey", classInfoGraphNode.Key));
  80. return propertyElement;
  81. }
  82. void CreateCollectionProperty(XPBaseObject selectedObject, IClassInfoGraphNode classInfoGraphNode, XElement root,
  83. XElement propertyElement) {
  84. XPMemberInfo memberInfo = selectedObject.ClassInfo.FindMember(classInfoGraphNode.Name);
  85. if (memberInfo != null) {
  86. var theObjects = (IEnumerable)memberInfo.GetValue(selectedObject);
  87. foreach (XPBaseObject theObject in theObjects) {
  88. CreateRefElelement(classInfoGraphNode,theObject.GetType().Name, root, theObject, propertyElement);
  89. }
  90. }
  91. }
  92. void CreateRefElelement(IClassInfoGraphNode classInfoGraphNode, string typeName, XElement root, XPBaseObject theObject, XElement propertyElement) {
  93. var serializedObjectRefElement = new XElement("SerializedObjectRef");
  94. propertyElement.Add(serializedObjectRefElement);
  95. serializedObjectRefElement.Add(new XAttribute("type", typeName));
  96. serializedObjectRefElement.Add(new XAttribute("strategy", classInfoGraphNode.SerializationStrategy));
  97. if (theObject != null) {
  98. IEnumerable<IClassInfoGraphNode> classInfoGraphNodes = _serializeClassInfoGraphNodesCalculator.GetSerializedClassInfoGraphNodes(theObject, typeName);
  99. CreateRefKeyElements(classInfoGraphNodes, theObject, serializedObjectRefElement);
  100. if (classInfoGraphNode.SerializationStrategy == SerializationStrategy.SerializeAsObject)
  101. ExportCore(theObject, classInfoGraphNodes, root);
  102. }
  103. }
  104. void CreateRefKeyElements(IEnumerable<IClassInfoGraphNode> serializedClassInfoGraphNodes, XPBaseObject theObject, XElement serializedObjectRefElement) {
  105. foreach (var infoGraphNode in serializedClassInfoGraphNodes.Where(node => node.Key)) {
  106. var serializedObjectRefKeyElement = new XElement("Key");
  107. serializedObjectRefKeyElement.Add(new XAttribute("name",infoGraphNode.Name));
  108. serializedObjectRefKeyElement.Value = theObject.GetMemberValue(infoGraphNode.Name).ToString();
  109. serializedObjectRefElement.Add(serializedObjectRefKeyElement);
  110. }
  111. }
  112. void CreateObjectProperty(XPBaseObject selectedObject, XElement propertyElement, IClassInfoGraphNode classInfoGraphNode, XElement root) {
  113. XPMemberInfo memberInfo = selectedObject.ClassInfo.FindMember(classInfoGraphNode.Name);
  114. if (memberInfo != null) {
  115. var theObject = (XPBaseObject) memberInfo.GetValue(selectedObject);
  116. CreateRefElelement(classInfoGraphNode,theObject!= null?theObject.GetType().Name:memberInfo.MemberType.Name, root, theObject, propertyElement);
  117. }
  118. }
  119. public void Export(IEnumerable<XPBaseObject> xpBaseObjects, ISerializationConfigurationGroup serializationConfigurationGroup, string fileName) {
  120. var document = Export(xpBaseObjects, serializationConfigurationGroup);
  121. if (fileName != null) {
  122. var xmlWriterSettings = new XmlWriterSettings {
  123. OmitXmlDeclaration = true, Indent = true, NewLineChars = "\r\n", CloseOutput = true,
  124. };
  125. using (XmlWriter textWriter = XmlWriter.Create(new FileStream(fileName, FileMode.Create), xmlWriterSettings)) {
  126. document.Save(textWriter);
  127. textWriter.Close();
  128. }
  129. }
  130. }
  131. }
  132. }