1 // =================================
  2 // Copyright (c) 2024 Seppo Laakko
  3 // Distributed under the MIT license
  4 // =================================
  5 
  6 using System;
  7 using System.Collections;
  8 
  9 namespace System.Xml.Serialization
 10 {
 11     public concept XmlExportableClassType<T>{
 12     {
 13         Result<System.Xml.Element*> T.ToXml(const string& fieldName);
 14         Result<System.Xml.Element*> T.ToXml(const string& fieldNameXmlSerializationContext& ctx);}
 15     }
 16 
 17     public concept XmlExportableScalarType<T>{
 18     {
 19         where
 20             T is bool or 
 21             T is sbyte or 
 22             T is byte or 
 23             T is short or 
 24             T is ushort or 
 25             T is int or 
 26             T is uint or 
 27             T is long or 
 28             T is ulong or 
 29             T is float or 
 30             T is double or 
 31             T is char or 
 32             T is wchar or 
 33             T is uchar;}
 34     }
 35 
 36     public concept XmlExportableEnumeratedType<T>{
 37     {
 38         where System.Meta.IsEnumeratedType<T>();}
 39     }
 40 
 41     public concept XmlExportableTimeType<T>{
 42     {
 43         where T is System.Date or T is System.DateTime;}
 44     }
 45 
 46     public concept XmlExportable<T>{
 47     {
 48         where
 49             T is XmlExportableClassType or 
 50             T is XmlExportableScalarType or 
 51             T is XmlExportableEnumeratedType or 
 52             T is XmlExportableTimeType or 
 53             T is string or 
 54             T is wstring or 
 55             T is ustring or 
 56             T is System.TimePoint or 
 57             T is System.Duration or 
 58             T is System.Uuid;}
 59     }
 60 
 61     public Result<System.Xml.Element*> ToXml(const System.Uuid& valueconst string& fieldNameXmlSerializationContext& ctx)
 62     {
 63         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
 64         auto stringResult = ToString(value);
 65         if (stringResult.Error()) return Result<System.Xml.Element*>(ErrorId(stringResult.GetErrorId()));
 66         element->SetAttribute("value"stringResult.Value());
 67         return Result<System.Xml.Element*>(element.Release());
 68     }
 69 
 70     public Result<System.Xml.Element*> ToXml<T>(const T& objectconst string& fieldNameXmlSerializationContext& ctx)
 71         where T is XmlExportableClassType
 72     {
 73         auto result = object.ToXml(fieldNamectx);
 74         if (result.Error()) return Result<System.Xml.Element*>(ErrorId(result.GetErrorId()));
 75         System.Xml.Element* xmlElement = result.Value();
 76         UniquePtr<System.Xml.Element> element(xmlElement);
 77         if (!ctx.GetFlag(System.Xml.Serialization.XmlSerializationFlags.suppressMetadata))
 78         {
 79             int classId = object.ClassId();
 80             element->SetAttribute("classId"ToString(classId));
 81         }
 82         return Result<System.Xml.Element*>(element.Release());
 83     }
 84 
 85     public Result<System.Xml.Element*> ToXml<T>(const UniquePtr<T>& objectPtrconst string& fieldNameXmlSerializationContext& ctx)
 86         where T is XmlExportableClassType
 87     {
 88         if (objectPtr.IsNull())
 89         {
 90             UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
 91             element->SetAttribute("value""null");
 92             return Result<System.Xml.Element*>(element.Release());
 93         }
 94         else
 95         {
 96             auto result = objectPtr->ToXml(fieldNamectx);
 97             if (result.Error()) return Result<System.Xml.Element*>(ErrorId(result.GetErrorId()));
 98             System.Xml.Element* xmlElement = result.Value();
 99             UniquePtr<System.Xml.Element> element(xmlElement);
100             if (!ctx.GetFlag(System.Xml.Serialization.XmlSerializationFlags.suppressMetadata))
101             {
102                 int classId = objectPtr->ClassId();
103                 element->SetAttribute("classId"ToString(classId));
104             }
105             return Result<System.Xml.Element*>(element.Release());
106         }
107     }
108 
109     public Result<System.Xml.Element*> ToXml<T>(const SharedPtr<T>& objectPtrconst string& fieldNameXmlSerializationContext& ctx)
110         where T is XmlExportableClassType
111     {
112         if (objectPtr.IsNull())
113         {
114             UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
115             element->SetAttribute("value""null");
116             return Result<System.Xml.Element*>(element.Release());
117         }
118         else
119         {
120             auto result = objectPtr->ToXml(fieldNamectx);
121             if (result.Error()) return Result<System.Xml.Element*>(ErrorId(result.GetErrorId()));
122             System.Xml.Element* xmlElement = result.Value();
123             UniquePtr<System.Xml.Element> element(xmlElement);
124             if (!ctx.GetFlag(System.Xml.Serialization.XmlSerializationFlags.suppressMetadata))
125             {
126                 int classId = objectPtr->ClassId();
127                 element->SetAttribute("classId"ToString(classId));
128             }
129             return Result<System.Xml.Element*>(element.Release());
130         }
131     }
132 
133     public Result<System.Xml.Element*> ToXml<T>(const XmlPtr<T>& xmlPtrconst string& fieldNameXmlSerializationContext& ctx)
134         where T is XmlExportableClassType
135     {
136         if (xmlPtr.IsNull())
137         {
138             UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
139             element->SetAttribute("value""null");
140             return Result<System.Xml.Element*>(element.Release());
141         }
142         else
143         {
144             UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
145             auto result = ToString(xmlPtr.TargetObjectId());
146             if (result.Error()) return Result<System.Xml.Element*>(ErrorId(result.GetErrorId()));
147             string objectIdStr = Rvalue(result.Value());
148             element->SetAttribute("objectId"objectIdStr);
149             return Result<System.Xml.Element*>(element.Release());
150         }
151     }
152 
153     public Result<System.Xml.Element*> ToXml<T>(const List<T>& listconst string& fieldNameXmlSerializationContext& ctx)
154         where T is XmlExportable
155     {
156         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
157         for (const T& item : list)
158         {
159             auto result = ToXml(item"item"ctx);
160             if (result.Error()) return Result<System.Xml.Element*>(ErrorId(result.GetErrorId()));
161             System.Xml.Element* xmlElement = result.Value();
162             element->AppendChild(xmlElement);
163         }
164         return Result<System.Xml.Element*>(element.Release());
165     }
166 
167     public Result<System.Xml.Element*> ToXml<T>(const List<UniquePtr<T>>& listconst string& fieldNameXmlSerializationContext& ctx)
168         where T is XmlExportableClassType
169     {
170         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
171         for (const UniquePtr<T>& item : list)
172         {
173             auto result = ToXml(item"item"ctx);
174             if (result.Error()) return Result<System.Xml.Element*>(ErrorId(result.GetErrorId()));
175             System.Xml.Element* xmlElement = result.Value();
176             element->AppendChild(xmlElement);
177         }
178         return Result<System.Xml.Element*>(element.Release());
179     }
180 
181     public Result<System.Xml.Element*> ToXml<T>(const List<SharedPtr<T>>& listconst string& fieldNameXmlSerializationContext& ctx)
182         where T is XmlExportableClassType
183     {
184         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
185         for (const SharedPtr<T>& item : list)
186         {
187             auto result = ToXml(item"item"ctx);
188             if (result.Error()) return Result<System.Xml.Element*>(ErrorId(result.GetErrorId()));
189             System.Xml.Element* xmlElement = result.Value();
190             element->AppendChild(xmlElement);
191         }
192         return Result<System.Xml.Element*>(element.Release());
193     }
194 
195     public Result<System.Xml.Element*> ToXml<T>(const List<XmlPtr<T>>& listconst string& fieldNameXmlSerializationContext& ctx)
196         where T is XmlExportableClassType
197     {
198         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
199         for (const XmlPtr<T>& item : list)
200         {
201             auto result = ToXml(item"item"ctx);
202             if (result.Error()) return Result<System.Xml.Element*>(ErrorId(result.GetErrorId()));
203             System.Xml.Element* xmlElement = result.Value();
204             element->AppendChild(xmlElement);
205         }
206         return Result<System.Xml.Element*>(element.Release());
207     }
208 
209     public Result<System.Xml.Element*> ToXml(const string& valueconst string& fieldNameXmlSerializationContext& ctx)
210     {
211         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
212         element->SetAttribute("value"value);
213         return Result<System.Xml.Element*>(element.Release());
214     }
215 
216     public Result<System.Xml.Element*> ToXml(const wstring& valueconst string& fieldNameXmlSerializationContext& ctx)
217     {
218         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
219         auto utf8Result = ToUtf8(value);
220         if (utf8Result.Error()) return Result<System.Xml.Element*>(ErrorId(utf8Result.GetErrorId()));
221         element->SetAttribute("value"utf8Result.Value());
222         return Result<System.Xml.Element*>(element.Release());
223     }
224 
225     public Result<System.Xml.Element*> ToXml(const ustring& valueconst string& fieldNameXmlSerializationContext& ctx)
226     {
227         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
228         auto utf8Result = ToUtf8(value);
229         if (utf8Result.Error()) return Result<System.Xml.Element*>(ErrorId(utf8Result.GetErrorId()));
230         element->SetAttribute("value"utf8Result.Value());
231         return Result<System.Xml.Element*>(element.Release());
232     }
233 
234     public Result<System.Xml.Element*> ToXml(const System.TimePoint& valueconst string& fieldNameXmlSerializationContext& ctx)
235     {
236         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
237         element->SetAttribute("value"ToString(value.Rep()));
238         return Result<System.Xml.Element*>(element.Release());
239     }
240 
241     public Result<System.Xml.Element*> ToXml(const System.Duration& valueconst string& fieldNameXmlSerializationContext& ctx)
242     {
243         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
244         element->SetAttribute("value"ToString(value.Rep()));
245         return Result<System.Xml.Element*>(element.Release());
246     }
247 
248     public Result<System.Xml.Element*> ToXml<T>(const T& valueconst string& fieldNameXmlSerializationContext& ctx)
249         where T is XmlExportableScalarType
250     {
251         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
252         element->SetAttribute("value"ToString(value));
253         return Result<System.Xml.Element*>(element.Release());
254     }
255 
256     public Result<System.Xml.Element*> ToXml<T>(T valueconst string& fieldNameXmlSerializationContext& ctx)
257         where T is XmlExportableEnumeratedType
258     {
259         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
260         T.UnderlyingType x = cast<T.UnderlyingType>(value);
261         element->SetAttribute("value"ToString(cast<long>(x)));
262         return Result<System.Xml.Element*>(element.Release());
263     }
264 
265     public Result<System.Xml.Element*> ToXml(const System.Date& valueconst string& fieldNameXmlSerializationContext& ctx)
266     {
267         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
268         element->SetAttribute("value"value.ToString());
269         return Result<System.Xml.Element*>(element.Release());
270     }
271 
272     public Result<System.Xml.Element*> ToXml(const System.DateTime& valueconst string& fieldNameXmlSerializationContext& ctx)
273     {
274         UniquePtr<System.Xml.Element> element(System.Xml.MakeElement(fieldName));
275         element->SetAttribute("value"value.ToString());
276         return Result<System.Xml.Element*>(element.Release());
277     }
278 }