source: branches/PersistenceOverhaul/HeuristicLab.Tests/HeuristicLab.Persistence-3.3/UseCases.cs @ 13386

Last change on this file since 13386 was 13386, checked in by ascheibe, 4 years ago

#2520

  • fixed duplicate guids
  • adapted/added unit tests for new persistence
File size: 54.0 KB
Line 
1#region License Information
2/* HeuristicLab
3 * Copyright (C) 2002-2015 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
4 *
5 * This file is part of HeuristicLab.
6 *
7 * HeuristicLab is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * HeuristicLab is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
19 */
20#endregion
21
22using System;
23using System.Collections;
24using System.Collections.Generic;
25using System.Drawing;
26using System.Globalization;
27using System.IO;
28using System.Linq;
29using System.Reflection;
30using System.Text;
31using System.Text.RegularExpressions;
32using System.Threading.Tasks;
33using HeuristicLab.Algorithms.GeneticAlgorithm;
34using HeuristicLab.Persistence.Auxiliary;
35using HeuristicLab.Persistence.Core;
36using HeuristicLab.Persistence.Core.Tokens;
37using HeuristicLab.Persistence.Default.CompositeSerializers;
38using HeuristicLab.Persistence.Default.CompositeSerializers.Storable;
39using HeuristicLab.Persistence.Default.DebugString;
40using HeuristicLab.Persistence.Default.Xml;
41using HeuristicLab.Persistence.Default.Xml.Primitive;
42using HeuristicLab.Persistence.Interfaces;
43using HeuristicLab.Tests;
44using Microsoft.VisualStudio.TestTools.UnitTesting;
45
46namespace HeuristicLab.Persistence.Tests {
47
48  [StorableClass("777E5793-7389-4109-A617-D7D6EB74A2C7")]
49  public class NumberTest {
50    [Storable]
51    private bool _bool = true;
52    [Storable]
53    private byte _byte = 0xFF;
54    [Storable]
55    private sbyte _sbyte = 0xF;
56    [Storable]
57    private short _short = -123;
58    [Storable]
59    private ushort _ushort = 123;
60    [Storable]
61    private int _int = -123;
62    [Storable]
63    private uint _uint = 123;
64    [Storable]
65    private long _long = 123456;
66    [Storable]
67    private ulong _ulong = 123456;
68    public override bool Equals(object obj) {
69      NumberTest nt = obj as NumberTest;
70      if (nt == null)
71        throw new NotSupportedException();
72      return
73        nt._bool == _bool &&
74        nt._byte == _byte &&
75        nt._sbyte == _sbyte &&
76        nt._short == _short &&
77        nt._ushort == _ushort &&
78        nt._int == _int &&
79        nt._uint == _uint &&
80        nt._long == _long &&
81        nt._ulong == _ulong;
82    }
83    public override int GetHashCode() {
84      return
85        _bool.GetHashCode() ^
86        _byte.GetHashCode() ^
87        _sbyte.GetHashCode() ^
88        _short.GetHashCode() ^
89        _short.GetHashCode() ^
90        _int.GetHashCode() ^
91        _uint.GetHashCode() ^
92        _long.GetHashCode() ^
93        _ulong.GetHashCode();
94    }
95  }
96
97  [StorableClass("2911C342-74AB-4B47-9840-87F012AEF0C1")]
98  public class NonDefaultConstructorClass {
99    [Storable]
100    int value;
101    public NonDefaultConstructorClass(int value) {
102      this.value = value;
103    }
104  }
105
106  [StorableClass("8621F4FA-8711-4DA4-A50B-7D04683440B8")]
107  public class IntWrapper {
108
109    [Storable]
110    public int Value;
111
112    private IntWrapper() { }
113
114    public IntWrapper(int value) {
115      this.Value = value;
116    }
117
118    public override bool Equals(object obj) {
119      if (obj as IntWrapper == null)
120        return false;
121      return Value.Equals(((IntWrapper)obj).Value);
122    }
123    public override int GetHashCode() {
124      return Value.GetHashCode();
125    }
126
127  }
128
129  [StorableClass("0B93C65E-1A4C-45DD-B40D-7614BA2B2ABA")]
130  public class PrimitivesTest : NumberTest {
131    [Storable]
132    private char c = 'e';
133    [Storable]
134    private long[,] _long_array =
135      new long[,] { { 123, 456, }, { 789, 123 } };
136    [Storable]
137    public List<int> list = new List<int> { 1, 2, 3, 4, 5 };
138    [Storable]
139    private object o = new object();
140    public override bool Equals(object obj) {
141      PrimitivesTest pt = obj as PrimitivesTest;
142      if (pt == null)
143        throw new NotSupportedException();
144      return base.Equals(obj) &&
145        c == pt.c &&
146        _long_array == pt._long_array &&
147        list == pt.list &&
148        o == pt.o;
149    }
150    public override int GetHashCode() {
151      return base.GetHashCode() ^
152        c.GetHashCode() ^
153        _long_array.GetHashCode() ^
154        list.GetHashCode() ^
155        o.GetHashCode();
156    }
157  }
158
159  public enum TestEnum { va1, va2, va3, va8 } ;
160
161  [StorableClass("0DA4A6A5-0280-4F3C-80DA-0AB09461F66C")]
162  public class RootBase {
163    [Storable]
164    private string baseString = "   Serial  ";
165    [Storable]
166    public TestEnum myEnum = TestEnum.va3;
167    public override bool Equals(object obj) {
168      RootBase rb = obj as RootBase;
169      if (rb == null)
170        throw new NotSupportedException();
171      return baseString == rb.baseString &&
172        myEnum == rb.myEnum;
173    }
174    public override int GetHashCode() {
175      return baseString.GetHashCode() ^
176        myEnum.GetHashCode();
177    }
178  }
179
180  [StorableClass("12CC2626-A1E2-45A5-9761-902333C88CCF")]
181  public class Root : RootBase {
182    [Storable]
183    public Stack<int> intStack = new Stack<int>();
184    [Storable]
185    public int[] i = new[] { 3, 4, 5, 6 };
186    [Storable(Name = "Test String")]
187    public string s;
188    [Storable]
189    public ArrayList intArray = new ArrayList(new[] { 1, 2, 3 });
190    [Storable]
191    public List<int> intList = new List<int>(new[] { 321, 312, 321 });
192    [Storable]
193    public Custom c;
194    [Storable]
195    public List<Root> selfReferences;
196    [Storable]
197    public double[,] multiDimArray = new double[,] { { 1, 2, 3 }, { 3, 4, 5 } };
198    [Storable]
199    public bool boolean = true;
200    [Storable]
201    public DateTime dateTime;
202    [Storable]
203    public KeyValuePair<string, int> kvp = new KeyValuePair<string, int>("Serial", 123);
204    [Storable]
205    public Dictionary<string, int> dict = new Dictionary<string, int>();
206    [Storable(DefaultValue = "default")]
207    public string uninitialized;
208  }
209
210  public enum SimpleEnum { one, two, three }
211  public enum ComplexEnum { one = 1, two = 2, three = 3 }
212  [FlagsAttribute]
213  public enum TrickyEnum { zero = 0, one = 1, two = 2 }
214
215  [StorableClass("04BFD8AF-AB93-457A-B5CD-F2AB2B18874F")]
216  public class EnumTest {
217    [Storable]
218    public SimpleEnum simpleEnum = SimpleEnum.one;
219    [Storable]
220    public ComplexEnum complexEnum = (ComplexEnum)2;
221    [Storable]
222    public TrickyEnum trickyEnum = (TrickyEnum)15;
223  }
224
225  [StorableClass("41E5C615-82A6-4844-B6A4-4DB8ED8C03D8")]
226  public class Custom {
227    [Storable]
228    public int i;
229    [Storable]
230    public Root r;
231    [Storable]
232    public string name = "<![CDATA[<![CDATA[Serial]]>]]>";
233  }
234
235  [StorableClass("3D2455E6-0AD9-4141-B44A-759F71491443")]
236  public class Manager {
237
238    public DateTime lastLoadTime;
239    [Storable]
240    private DateTime lastLoadTimePersistence {
241      get { return lastLoadTime; }
242      set { lastLoadTime = DateTime.Now; }
243    }
244    [Storable]
245    public double? dbl;
246  }
247
248  [StorableClass("D8D40F6E-91DC-4E20-8154-F95C0AF32CC8")]
249  public class C {
250    [Storable]
251    public C[][] allCs;
252    [Storable]
253    public KeyValuePair<List<C>, C> kvpList;
254  }
255
256  public class NonSerializable {
257    int x = 0;
258    public override bool Equals(object obj) {
259      NonSerializable ns = obj as NonSerializable;
260      if (ns == null)
261        throw new NotSupportedException();
262      return ns.x == x;
263    }
264    public override int GetHashCode() {
265      return x.GetHashCode();
266    }
267  }
268
269
270  [TestClass]
271  public class UseCases {
272
273    private string tempFile;
274
275    [TestInitialize()]
276    public void CreateTempFile() {
277      tempFile = Path.GetTempFileName();
278    }
279
280    [TestCleanup()]
281    public void ClearTempFile() {
282      StreamReader reader = new StreamReader(tempFile);
283      string s = reader.ReadToEnd();
284      reader.Close();
285      File.Delete(tempFile);
286    }
287
288    [TestMethod]
289    [TestCategory("Persistence")]
290    [TestProperty("Time", "short")]
291    public void ComplexStorable() {
292      Root r = InitializeComplexStorable();
293      XmlGenerator.Serialize(r, tempFile);
294      Root newR = (Root)XmlParser.Deserialize(tempFile);
295      CompareComplexStorables(r, newR);
296    }
297
298    [TestMethod]
299    [TestCategory("Persistence")]
300    [TestProperty("Time", "short")]
301    public void ComplexEasyStorable() {
302      Root r = InitializeComplexStorable();
303      ReadableXmlGenerator.Serialize(r, tempFile);
304      using (var reader = new StreamReader(tempFile)) {
305        string text = reader.ReadToEnd();
306        Assert.IsTrue(text.StartsWith("<Root"));
307      }
308    }
309
310    private static void CompareComplexStorables(Root r, Root newR) {
311      Assert.AreEqual(
312        DebugStringGenerator.Serialize(r),
313        DebugStringGenerator.Serialize(newR));
314      Assert.AreSame(newR, newR.selfReferences[0]);
315      Assert.AreNotSame(r, newR);
316      Assert.AreEqual(r.myEnum, TestEnum.va1);
317      Assert.AreEqual(r.i[0], 7);
318      Assert.AreEqual(r.i[1], 5);
319      Assert.AreEqual(r.i[2], 6);
320      Assert.AreEqual(r.s, "new value");
321      Assert.AreEqual(r.intArray[0], 3);
322      Assert.AreEqual(r.intArray[1], 2);
323      Assert.AreEqual(r.intArray[2], 1);
324      Assert.AreEqual(r.intList[0], 9);
325      Assert.AreEqual(r.intList[1], 8);
326      Assert.AreEqual(r.intList[2], 7);
327      Assert.AreEqual(r.multiDimArray[0, 0], 5);
328      Assert.AreEqual(r.multiDimArray[0, 1], 4);
329      Assert.AreEqual(r.multiDimArray[0, 2], 3);
330      Assert.AreEqual(r.multiDimArray[1, 0], 1);
331      Assert.AreEqual(r.multiDimArray[1, 1], 4);
332      Assert.AreEqual(r.multiDimArray[1, 2], 6);
333      Assert.IsFalse(r.boolean);
334      Assert.IsTrue((DateTime.Now - r.dateTime).TotalSeconds < 10);
335      Assert.AreEqual(r.kvp.Key, "string key");
336      Assert.AreEqual(r.kvp.Value, 321);
337      Assert.IsNull(r.uninitialized);
338      Assert.AreEqual(newR.myEnum, TestEnum.va1);
339      Assert.AreEqual(newR.i[0], 7);
340      Assert.AreEqual(newR.i[1], 5);
341      Assert.AreEqual(newR.i[2], 6);
342      Assert.AreEqual(newR.s, "new value");
343      Assert.AreEqual(newR.intArray[0], 3);
344      Assert.AreEqual(newR.intArray[1], 2);
345      Assert.AreEqual(newR.intArray[2], 1);
346      Assert.AreEqual(newR.intList[0], 9);
347      Assert.AreEqual(newR.intList[1], 8);
348      Assert.AreEqual(newR.intList[2], 7);
349      Assert.AreEqual(newR.multiDimArray[0, 0], 5);
350      Assert.AreEqual(newR.multiDimArray[0, 1], 4);
351      Assert.AreEqual(newR.multiDimArray[0, 2], 3);
352      Assert.AreEqual(newR.multiDimArray[1, 0], 1);
353      Assert.AreEqual(newR.multiDimArray[1, 1], 4);
354      Assert.AreEqual(newR.multiDimArray[1, 2], 6);
355      Assert.AreEqual(newR.intStack.Pop(), 3);
356      Assert.AreEqual(newR.intStack.Pop(), 2);
357      Assert.AreEqual(newR.intStack.Pop(), 1);
358      Assert.IsFalse(newR.boolean);
359      Assert.IsTrue((DateTime.Now - newR.dateTime).TotalSeconds < 10);
360      Assert.AreEqual(newR.kvp.Key, "string key");
361      Assert.AreEqual(newR.kvp.Value, 321);
362      Assert.IsNull(newR.uninitialized);
363    }
364
365    private static Root InitializeComplexStorable() {
366      Root r = new Root();
367      r.intStack.Push(1);
368      r.intStack.Push(2);
369      r.intStack.Push(3);
370      r.selfReferences = new List<Root> { r, r };
371      r.c = new Custom { r = r };
372      r.dict.Add("one", 1);
373      r.dict.Add("two", 2);
374      r.dict.Add("three", 3);
375      r.myEnum = TestEnum.va1;
376      r.i = new[] { 7, 5, 6 };
377      r.s = "new value";
378      r.intArray = new ArrayList { 3, 2, 1 };
379      r.intList = new List<int> { 9, 8, 7 };
380      r.multiDimArray = new double[,] { { 5, 4, 3 }, { 1, 4, 6 } };
381      r.boolean = false;
382      r.dateTime = DateTime.Now;
383      r.kvp = new KeyValuePair<string, int>("string key", 321);
384      r.uninitialized = null;
385
386      return r;
387    }
388
389    [TestMethod]
390    [TestCategory("Persistence")]
391    [TestProperty("Time", "short")]
392    public void SelfReferences() {
393      C c = new C();
394      C[][] cs = new C[2][];
395      cs[0] = new C[] { c };
396      cs[1] = new C[] { c };
397      c.allCs = cs;
398      c.kvpList = new KeyValuePair<List<C>, C>(new List<C> { c }, c);
399      XmlGenerator.Serialize(cs, tempFile);
400      object o = XmlParser.Deserialize(tempFile);
401      Assert.AreEqual(
402        DebugStringGenerator.Serialize(cs),
403        DebugStringGenerator.Serialize(o));
404      Assert.AreSame(c, c.allCs[0][0]);
405      Assert.AreSame(c, c.allCs[1][0]);
406      Assert.AreSame(c, c.kvpList.Key[0]);
407      Assert.AreSame(c, c.kvpList.Value);
408      C[][] newCs = (C[][])o;
409      C newC = newCs[0][0];
410      Assert.AreSame(newC, newC.allCs[0][0]);
411      Assert.AreSame(newC, newC.allCs[1][0]);
412      Assert.AreSame(newC, newC.kvpList.Key[0]);
413      Assert.AreSame(newC, newC.kvpList.Value);
414    }
415
416    [TestMethod]
417    [TestCategory("Persistence")]
418    [TestProperty("Time", "short")]
419    public void ArrayCreation() {
420      ArrayList[] arrayListArray = new ArrayList[4];
421      arrayListArray[0] = new ArrayList();
422      arrayListArray[0].Add(arrayListArray);
423      arrayListArray[0].Add(arrayListArray);
424      arrayListArray[1] = new ArrayList();
425      arrayListArray[1].Add(arrayListArray);
426      arrayListArray[2] = new ArrayList();
427      arrayListArray[2].Add(arrayListArray);
428      arrayListArray[2].Add(arrayListArray);
429      Array a = Array.CreateInstance(
430                              typeof(object),
431                              new[] { 1, 2 }, new[] { 3, 4 });
432      arrayListArray[2].Add(a);
433      XmlGenerator.Serialize(arrayListArray, tempFile);
434      object o = XmlParser.Deserialize(tempFile);
435      Assert.AreEqual(
436        DebugStringGenerator.Serialize(arrayListArray),
437        DebugStringGenerator.Serialize(o));
438      ArrayList[] newArray = (ArrayList[])o;
439      Assert.AreSame(arrayListArray, arrayListArray[0][0]);
440      Assert.AreSame(arrayListArray, arrayListArray[2][1]);
441      Assert.AreSame(newArray, newArray[0][0]);
442      Assert.AreSame(newArray, newArray[2][1]);
443    }
444
445    [TestMethod]
446    [TestCategory("Persistence")]
447    [TestProperty("Time", "short")]
448    public void CustomSerializationProperty() {
449      Manager m = new Manager();
450      XmlGenerator.Serialize(m, tempFile);
451      Manager newM = (Manager)XmlParser.Deserialize(tempFile);
452      Assert.AreNotEqual(
453        DebugStringGenerator.Serialize(m),
454        DebugStringGenerator.Serialize(newM));
455      Assert.AreEqual(m.dbl, newM.dbl);
456      Assert.AreEqual(m.lastLoadTime, new DateTime());
457      Assert.AreNotEqual(newM.lastLoadTime, new DateTime());
458      Assert.IsTrue((DateTime.Now - newM.lastLoadTime).TotalSeconds < 10);
459    }
460
461    [TestMethod]
462    [TestCategory("Persistence")]
463    [TestProperty("Time", "short")]
464    public void Primitives() {
465      PrimitivesTest sdt = new PrimitivesTest();
466      XmlGenerator.Serialize(sdt, tempFile);
467      object o = XmlParser.Deserialize(tempFile);
468      Assert.AreEqual(
469        DebugStringGenerator.Serialize(sdt),
470        DebugStringGenerator.Serialize(o));
471    }
472
473    [TestMethod]
474    [TestCategory("Persistence")]
475    [TestProperty("Time", "short")]
476    public void MultiDimensionalArray() {
477      string[,] mDimString = new string[,] {
478        {"ora", "et", "labora"},
479        {"Beten", "und", "Arbeiten"}
480      };
481      XmlGenerator.Serialize(mDimString, tempFile);
482      object o = XmlParser.Deserialize(tempFile);
483      Assert.AreEqual(
484        DebugStringGenerator.Serialize(mDimString),
485        DebugStringGenerator.Serialize(o));
486    }
487
488    [StorableClass("B2C78E8F-32F9-43BE-9DED-219F102125EB")]
489    public class NestedType {
490      [Storable]
491      private string value = "value";
492      public override bool Equals(object obj) {
493        NestedType nt = obj as NestedType;
494        if (nt == null)
495          throw new NotSupportedException();
496        return nt.value == value;
497      }
498      public override int GetHashCode() {
499        return value.GetHashCode();
500      }
501    }
502
503    [TestMethod]
504    [TestCategory("Persistence")]
505    [TestProperty("Time", "short")]
506    public void NestedTypeTest() {
507      NestedType t = new NestedType();
508      XmlGenerator.Serialize(t, tempFile);
509      object o = XmlParser.Deserialize(tempFile);
510      Assert.AreEqual(
511        DebugStringGenerator.Serialize(t),
512        DebugStringGenerator.Serialize(o));
513      Assert.IsTrue(t.Equals(o));
514    }
515
516
517    [TestMethod]
518    [TestCategory("Persistence")]
519    [TestProperty("Time", "short")]
520    public void SimpleArray() {
521      string[] strings = { "ora", "et", "labora" };
522      XmlGenerator.Serialize(strings, tempFile);
523      object o = XmlParser.Deserialize(tempFile);
524      Assert.AreEqual(
525        DebugStringGenerator.Serialize(strings),
526        DebugStringGenerator.Serialize(o));
527    }
528
529    [TestMethod]
530    [TestCategory("Persistence")]
531    [TestProperty("Time", "short")]
532    public void PrimitiveRoot() {
533      XmlGenerator.Serialize(12.3f, tempFile);
534      object o = XmlParser.Deserialize(tempFile);
535      Assert.AreEqual(
536        DebugStringGenerator.Serialize(12.3f),
537        DebugStringGenerator.Serialize(o));
538    }
539
540    private string formatFullMemberName(MemberInfo mi) {
541      return new StringBuilder()
542        .Append(mi.DeclaringType.Assembly.GetName().Name)
543        .Append(": ")
544        .Append(mi.DeclaringType.Namespace)
545        .Append('.')
546        .Append(mi.DeclaringType.Name)
547        .Append('.')
548        .Append(mi.Name).ToString();
549    }
550
551    public void CodingConventions() {
552      List<string> lowerCaseMethodNames = new List<string>();
553      List<string> lowerCaseProperties = new List<string>();
554      List<string> lowerCaseFields = new List<string>();
555      foreach (Assembly a in PluginLoader.Assemblies) {
556        if (!a.GetName().Name.StartsWith("HeuristicLab"))
557          continue;
558        foreach (Type t in a.GetTypes()) {
559          foreach (MemberInfo mi in t.GetMembers(BindingFlags.Public | BindingFlags.Instance | BindingFlags.Static)) {
560            if (mi.DeclaringType.Name.StartsWith("<>"))
561              continue;
562            if (char.IsLower(mi.Name[0])) {
563              if (mi.MemberType == MemberTypes.Field)
564                lowerCaseFields.Add(formatFullMemberName(mi));
565              if (mi.MemberType == MemberTypes.Property)
566                lowerCaseProperties.Add(formatFullMemberName(mi));
567              if (mi.MemberType == MemberTypes.Method &&
568                !mi.Name.StartsWith("get_") &&
569                !mi.Name.StartsWith("set_") &&
570                !mi.Name.StartsWith("add_") &&
571                !mi.Name.StartsWith("remove_") &&
572                !mi.Name.StartsWith("op_"))
573                lowerCaseMethodNames.Add(formatFullMemberName(mi));
574            }
575          }
576        }
577      }
578      //Assert.AreEqual("", lowerCaseFields.Aggregate("", (a, b) => a + "\r\n" + b));
579      Assert.AreEqual("", lowerCaseMethodNames.Aggregate("", (a, b) => a + "\r\n" + b));
580      Assert.AreEqual("", lowerCaseProperties.Aggregate("", (a, b) => a + "\r\n" + b));
581    }
582
583    [TestMethod]
584    [TestCategory("Persistence")]
585    [TestProperty("Time", "short")]
586    public void Number2StringDecomposer() {
587      NumberTest sdt = new NumberTest();
588      XmlGenerator.Serialize(sdt, tempFile,
589        new Configuration(new XmlFormat(),
590          new List<IPrimitiveSerializer> { new String2XmlSerializer() },
591          new List<ICompositeSerializer> { 
592            new StorableSerializer(),
593            new Number2StringSerializer() }));
594      object o = XmlParser.Deserialize(tempFile);
595      Assert.AreEqual(
596        DebugStringGenerator.Serialize(sdt),
597        DebugStringGenerator.Serialize(o));
598      Assert.IsTrue(sdt.Equals(o));
599    }
600
601    [TestMethod]
602    [TestCategory("Persistence")]
603    [TestProperty("Time", "short")]
604    public void Enums() {
605      EnumTest et = new EnumTest();
606      et.simpleEnum = SimpleEnum.two;
607      et.complexEnum = ComplexEnum.three;
608      et.trickyEnum = TrickyEnum.two | TrickyEnum.one;
609      XmlGenerator.Serialize(et, tempFile);
610      EnumTest newEt = (EnumTest)XmlParser.Deserialize(tempFile);
611      Assert.AreEqual(et.simpleEnum, SimpleEnum.two);
612      Assert.AreEqual(et.complexEnum, ComplexEnum.three);
613      Assert.AreEqual(et.trickyEnum, (TrickyEnum)3);
614    }
615
616    [TestMethod]
617    [TestCategory("Persistence")]
618    [TestProperty("Time", "short")]
619    public void TestAliasingWithOverriddenEquals() {
620      List<IntWrapper> ints = new List<IntWrapper>();
621      ints.Add(new IntWrapper(1));
622      ints.Add(new IntWrapper(1));
623      Assert.AreEqual(ints[0], ints[1]);
624      Assert.AreNotSame(ints[0], ints[1]);
625      XmlGenerator.Serialize(ints, tempFile);
626      List<IntWrapper> newInts = (List<IntWrapper>)XmlParser.Deserialize(tempFile);
627      Assert.AreEqual(newInts[0].Value, 1);
628      Assert.AreEqual(newInts[1].Value, 1);
629      Assert.AreEqual(newInts[0], newInts[1]);
630      Assert.AreNotSame(newInts[0], newInts[1]);
631    }
632
633    [TestMethod]
634    [TestCategory("Persistence")]
635    [TestProperty("Time", "short")]
636    public void NonDefaultConstructorTest() {
637      NonDefaultConstructorClass c = new NonDefaultConstructorClass(1);
638      try {
639        XmlGenerator.Serialize(c, tempFile);
640        Assert.Fail("Exception not thrown");
641      }
642      catch (PersistenceException) {
643      }
644    }
645
646    [TestMethod]
647    [TestCategory("Persistence")]
648    [TestProperty("Time", "short")]
649    public void TestSavingException() {
650      List<int> list = new List<int> { 1, 2, 3 };
651      XmlGenerator.Serialize(list, tempFile);
652      NonSerializable s = new NonSerializable();
653      try {
654        XmlGenerator.Serialize(s, tempFile);
655        Assert.Fail("Exception expected");
656      }
657      catch (PersistenceException) { }
658      List<int> newList = (List<int>)XmlParser.Deserialize(tempFile);
659      Assert.AreEqual(list[0], newList[0]);
660      Assert.AreEqual(list[1], newList[1]);
661    }
662
663    [TestMethod]
664    [TestCategory("Persistence")]
665    [TestProperty("Time", "short")]
666    public void TestTypeStringConversion() {
667      string name = typeof(List<int>[]).AssemblyQualifiedName;
668      string shortName =
669        "System.Collections.Generic.List`1[[System.Int32, mscorlib]][], mscorlib";
670      Assert.AreEqual(name, TypeNameParser.Parse(name).ToString());
671      Assert.AreEqual(shortName, TypeNameParser.Parse(name).ToString(false));
672      Assert.AreEqual(shortName, typeof(List<int>[]).VersionInvariantName());
673    }
674
675    [TestMethod]
676    [TestCategory("Persistence")]
677    [TestProperty("Time", "short")]
678    public void TestHexadecimalPublicKeyToken() {
679      string name = "TestClass, TestAssembly, Version=1.2.3.4, PublicKey=1234abc";
680      string shortName = "TestClass, TestAssembly";
681      Assert.AreEqual(name, TypeNameParser.Parse(name).ToString());
682      Assert.AreEqual(shortName, TypeNameParser.Parse(name).ToString(false));
683    }
684
685    [TestMethod]
686    [TestCategory("Persistence")]
687    [TestProperty("Time", "short")]
688    public void TestMultipleFailure() {
689      List<NonSerializable> l = new List<NonSerializable>();
690      l.Add(new NonSerializable());
691      l.Add(new NonSerializable());
692      l.Add(new NonSerializable());
693      try {
694        HeuristicLab.Persistence.Core.Serializer s = new HeuristicLab.Persistence.Core.Serializer(l,
695          ConfigurationService.Instance.GetConfiguration(new XmlFormat()),
696          "ROOT", true);
697        StringBuilder tokens = new StringBuilder();
698        foreach (var token in s) {
699          tokens.Append(token.ToString());
700        }
701        Assert.Fail("Exception expected");
702      }
703      catch (PersistenceException px) {
704        Assert.AreEqual(3, px.Data.Count);
705      }
706    }
707
708    [TestMethod]
709    [TestCategory("Persistence")]
710    [TestProperty("Time", "short")]
711    public void TestAssemblyVersionCheck() {
712      IntWrapper i = new IntWrapper(1);
713      HeuristicLab.Persistence.Core.Serializer s = new HeuristicLab.Persistence.Core.Serializer(i, ConfigurationService.Instance.GetDefaultConfig(new XmlFormat()));
714      XmlGenerator g = new XmlGenerator();
715      StringBuilder dataString = new StringBuilder();
716      foreach (var token in s) {
717        dataString.Append(g.Format(token));
718      }
719      StringBuilder typeString = new StringBuilder();
720      foreach (var line in g.Format(s.TypeCache))
721        typeString.Append(line);
722      Deserializer d = new Deserializer(XmlParser.ParseTypeCache(new StringReader(typeString.ToString())));
723      XmlParser p = new XmlParser(new StringReader(dataString.ToString()));
724      IntWrapper newI = (IntWrapper)d.Deserialize(p);
725      Assert.AreEqual(i.Value, newI.Value);
726
727      string newTypeString = Regex.Replace(typeString.ToString(),
728        "Version=\\d+\\.\\d+\\.\\d+\\.\\d+",
729        "Version=0.0.9999.9999");
730      try {
731        d = new Deserializer(XmlParser.ParseTypeCache(new StringReader(newTypeString)));
732        Assert.Fail("Exception expected");
733      }
734      catch (PersistenceException x) {
735        Assert.IsTrue(x.Message.Contains("incompatible"));
736      }
737      newTypeString = Regex.Replace(typeString.ToString(),
738        "Version=(\\d+\\.\\d+)\\.\\d+\\.\\d+",
739        "Version=$1.9999.9999");
740      try {
741        d = new Deserializer(XmlParser.ParseTypeCache(new StringReader(newTypeString)));
742        Assert.Fail("Exception expected");
743      }
744      catch (PersistenceException x) {
745        Assert.IsTrue(x.Message.Contains("newer"));
746      }
747    }
748
749    [TestMethod]
750    [TestCategory("Persistence")]
751    [TestProperty("Time", "short")]
752    public void InheritanceTest() {
753      New n = new New();
754      XmlGenerator.Serialize(n, tempFile);
755      New nn = (New)XmlParser.Deserialize(tempFile);
756      Assert.AreEqual(n.Name, nn.Name);
757      Assert.AreEqual(((Override)n).Name, ((Override)nn).Name);
758    }
759
760    [StorableClass("2B2FE809-CDA4-4BCD-BF4C-35F757678AB9")]
761    class Child {
762      [Storable]
763      public GrandParent grandParent;
764    }
765
766    [StorableClass("C8F4E805-26DF-4129-910E-F7F51E4DDE41")]
767    class Parent {
768      [Storable]
769      public Child child;
770    }
771
772    [StorableClass("0CF63740-F8C1-46EE-A3A0-7E350A8EBAA1")]
773    class GrandParent {
774      [Storable]
775      public Parent parent;
776    }
777
778    [TestMethod]
779    [TestCategory("Persistence")]
780    [TestProperty("Time", "short")]
781    public void InstantiateParentChainReference() {
782      GrandParent gp = new GrandParent();
783      gp.parent = new Parent();
784      gp.parent.child = new Child();
785      gp.parent.child.grandParent = gp;
786      Assert.AreSame(gp, gp.parent.child.grandParent);
787      XmlGenerator.Serialize(gp, tempFile);
788      GrandParent newGp = (GrandParent)XmlParser.Deserialize(tempFile);
789      Assert.AreSame(newGp, newGp.parent.child.grandParent);
790    }
791
792    struct TestStruct {
793      int value;
794      int PropertyValue { get; set; }
795      public TestStruct(int value)
796        : this() {
797        this.value = value;
798        PropertyValue = value;
799      }
800    }
801
802    [TestMethod]
803    [TestCategory("Persistence")]
804    [TestProperty("Time", "short")]
805    public void StructTest() {
806      TestStruct s = new TestStruct(10);
807      XmlGenerator.Serialize(s, tempFile);
808      TestStruct newS = (TestStruct)XmlParser.Deserialize(tempFile);
809      Assert.AreEqual(s, newS);
810    }
811
812    [TestMethod]
813    [TestCategory("Persistence")]
814    [TestProperty("Time", "short")]
815    public void PointTest() {
816      Point p = new Point(12, 34);
817      XmlGenerator.Serialize(p, tempFile);
818      Point newP = (Point)XmlParser.Deserialize(tempFile);
819      Assert.AreEqual(p, newP);
820    }
821
822    [TestMethod]
823    [TestCategory("Persistence")]
824    [TestProperty("Time", "short")]
825    public void NullableValueTypes() {
826      double?[] d = new double?[] { null, 1, 2, 3 };
827      XmlGenerator.Serialize(d, tempFile);
828      double?[] newD = (double?[])XmlParser.Deserialize(tempFile);
829      Assert.AreEqual(d[0], newD[0]);
830      Assert.AreEqual(d[1], newD[1]);
831      Assert.AreEqual(d[2], newD[2]);
832      Assert.AreEqual(d[3], newD[3]);
833    }
834
835    [TestMethod]
836    [TestCategory("Persistence")]
837    [TestProperty("Time", "short")]
838    public void BitmapTest() {
839      Icon icon = System.Drawing.SystemIcons.Hand;
840      Bitmap bitmap = icon.ToBitmap();
841      XmlGenerator.Serialize(bitmap, tempFile);
842      Bitmap newBitmap = (Bitmap)XmlParser.Deserialize(tempFile);
843
844      Assert.AreEqual(bitmap.Size, newBitmap.Size);
845      for (int i = 0; i < bitmap.Size.Width; i++)
846        for (int j = 0; j < bitmap.Size.Height; j++)
847          Assert.AreEqual(bitmap.GetPixel(i, j), newBitmap.GetPixel(i, j));
848    }
849
850    [StorableClass("F5920537-7F03-41C4-8061-8F8D7CDDB6BE")]
851    private class PersistenceHooks {
852      [Storable]
853      public int a;
854      [Storable]
855      public int b;
856      public int sum;
857      public bool WasSerialized { get; private set; }
858      [StorableHook(HookType.BeforeSerialization)]
859      void PreSerializationHook() {
860        WasSerialized = true;
861      }
862      [StorableHook(HookType.AfterDeserialization)]
863      void PostDeserializationHook() {
864        sum = a + b;
865      }
866    }
867
868    [TestMethod]
869    [TestCategory("Persistence")]
870    [TestProperty("Time", "short")]
871    public void HookTest() {
872      PersistenceHooks hookTest = new PersistenceHooks();
873      hookTest.a = 2;
874      hookTest.b = 5;
875      Assert.IsFalse(hookTest.WasSerialized);
876      Assert.AreEqual(hookTest.sum, 0);
877      XmlGenerator.Serialize(hookTest, tempFile);
878      Assert.IsTrue(hookTest.WasSerialized);
879      Assert.AreEqual(hookTest.sum, 0);
880      PersistenceHooks newHookTest = (PersistenceHooks)XmlParser.Deserialize(tempFile);
881      Assert.AreEqual(newHookTest.a, hookTest.a);
882      Assert.AreEqual(newHookTest.b, hookTest.b);
883      Assert.AreEqual(newHookTest.sum, newHookTest.a + newHookTest.b);
884      Assert.IsFalse(newHookTest.WasSerialized);
885    }
886
887    [StorableClass("935C5ECB-ACEF-48EA-93BC-4B4177DFE0A5")]
888    private class CustomConstructor {
889      public string Value = "none";
890      public CustomConstructor() {
891        Value = "default";
892      }
893      [StorableConstructor]
894      private CustomConstructor(bool deserializing) {
895        Assert.IsTrue(deserializing);
896        Value = "persistence";
897      }
898    }
899
900    [TestMethod]
901    [TestCategory("Persistence")]
902    [TestProperty("Time", "short")]
903    public void TestCustomConstructor() {
904      CustomConstructor cc = new CustomConstructor();
905      Assert.AreEqual(cc.Value, "default");
906      XmlGenerator.Serialize(cc, tempFile);
907      CustomConstructor newCC = (CustomConstructor)XmlParser.Deserialize(tempFile);
908      Assert.AreEqual(newCC.Value, "persistence");
909    }
910
911    [StorableClass("31D7CE01-E390-40CF-B9BF-BD79A8F850DA")]
912    public class ExplodingDefaultConstructor {
913      public ExplodingDefaultConstructor() {
914        throw new Exception("this constructor will always fail");
915      }
916      public ExplodingDefaultConstructor(string password) {
917      }
918    }
919
920    [TestMethod]
921    [TestCategory("Persistence")]
922    [TestProperty("Time", "short")]
923    public void TestConstructorExceptionUnwrapping() {
924      ExplodingDefaultConstructor x = new ExplodingDefaultConstructor("password");
925      XmlGenerator.Serialize(x, tempFile);
926      try {
927        ExplodingDefaultConstructor newX = (ExplodingDefaultConstructor)XmlParser.Deserialize(tempFile);
928        Assert.Fail("Exception expected");
929      }
930      catch (PersistenceException pe) {
931        Assert.AreEqual(pe.InnerException.Message, "this constructor will always fail");
932      }
933    }
934
935    [TestMethod]
936    [TestCategory("Persistence")]
937    [TestProperty("Time", "short")]
938    public void TestRejectionJustifications() {
939      NonSerializable ns = new NonSerializable();
940      try {
941        XmlGenerator.Serialize(ns, tempFile);
942        Assert.Fail("PersistenceException expected");
943      }
944      catch (PersistenceException x) {
945        Assert.IsTrue(x.Message.Contains(new StorableSerializer().JustifyRejection(typeof(NonSerializable))));
946      }
947    }
948
949    [TestMethod]
950    [TestCategory("Persistence")]
951    [TestProperty("Time", "short")]
952    public void TestStreaming() {
953      using (MemoryStream stream = new MemoryStream()) {
954        Root r = InitializeComplexStorable();
955        XmlGenerator.Serialize(r, stream);
956        using (MemoryStream stream2 = new MemoryStream(stream.ToArray())) {
957          Root newR = (Root)XmlParser.Deserialize(stream2);
958          CompareComplexStorables(r, newR);
959        }
960      }
961    }
962
963    [StorableClass("9DEE1F8F-320C-401B-8103-65FBA6BD4F07")]
964    public class HookInheritanceTestBase {
965      [Storable]
966      public object a;
967      public object link;
968      [StorableHook(HookType.AfterDeserialization)]
969      private void relink() {
970        link = a;
971      }
972    }
973
974    [StorableClass("97DF2931-2B23-4FAA-8E59-806FA58ADAED")]
975    public class HookInheritanceTestDerivedClass : HookInheritanceTestBase {
976      [Storable]
977      public object b;
978      [StorableHook(HookType.AfterDeserialization)]
979      private void relink() {
980        Assert.AreSame(a, link);
981        link = b;
982      }
983    }
984
985    [TestMethod]
986    [TestCategory("Persistence")]
987    [TestProperty("Time", "short")]
988    public void TestLinkInheritance() {
989      HookInheritanceTestDerivedClass c = new HookInheritanceTestDerivedClass();
990      c.a = new object();
991      XmlGenerator.Serialize(c, tempFile);
992      HookInheritanceTestDerivedClass newC = (HookInheritanceTestDerivedClass)XmlParser.Deserialize(tempFile);
993      Assert.AreSame(c.b, c.link);
994    }
995
996    [StorableClass(StorableClassType.AllFields, "6207E4E1-4CFC-4890-9741-33B7E1E43F26")]
997    public class AllFieldsStorable {
998      public int Value1 = 1;
999      [Storable]
1000      public int Value2 = 2;
1001      public int Value3 { get; private set; }
1002      public int Value4 { get; private set; }
1003      [StorableConstructor]
1004      public AllFieldsStorable(bool isDeserializing) {
1005        if (!isDeserializing) {
1006          Value1 = 12;
1007          Value2 = 23;
1008          Value3 = 34;
1009          Value4 = 56;
1010        }
1011      }
1012    }
1013
1014    [TestMethod]
1015    [TestCategory("Persistence")]
1016    [TestProperty("Time", "short")]
1017    public void TestStorableClassDiscoveryAllFields() {
1018      AllFieldsStorable afs = new AllFieldsStorable(false);
1019      XmlGenerator.Serialize(afs, tempFile);
1020      AllFieldsStorable newAfs = (AllFieldsStorable)XmlParser.Deserialize(tempFile);
1021      Assert.AreEqual(afs.Value1, newAfs.Value1);
1022      Assert.AreEqual(afs.Value2, newAfs.Value2);
1023      Assert.AreEqual(0, newAfs.Value3);
1024      Assert.AreEqual(0, newAfs.Value4);
1025    }
1026
1027    [StorableClass(StorableClassType.AllProperties, "ADDB5A7C-4BA9-4E5F-BFAF-2B48C8646808")]
1028    public class AllPropertiesStorable {
1029      public int Value1 = 1;
1030      [Storable]
1031      public int Value2 = 2;
1032      public int Value3 { get; private set; }
1033      public int Value4 { get; private set; }
1034      [StorableConstructor]
1035      public AllPropertiesStorable(bool isDeserializing) {
1036        if (!isDeserializing) {
1037          Value1 = 12;
1038          Value2 = 23;
1039          Value3 = 34;
1040          Value4 = 56;
1041        }
1042      }
1043    }
1044
1045    [TestMethod]
1046    [TestCategory("Persistence")]
1047    [TestProperty("Time", "short")]
1048    public void TestStorableClassDiscoveryAllProperties() {
1049      AllPropertiesStorable afs = new AllPropertiesStorable(false);
1050      XmlGenerator.Serialize(afs, tempFile);
1051      AllPropertiesStorable newAfs = (AllPropertiesStorable)XmlParser.Deserialize(tempFile);
1052      Assert.AreEqual(1, newAfs.Value1);
1053      Assert.AreEqual(2, newAfs.Value2);
1054      Assert.AreEqual(afs.Value3, newAfs.Value3);
1055      Assert.AreEqual(afs.Value4, newAfs.Value4);
1056
1057    }
1058
1059    [StorableClass(StorableClassType.AllFieldsAndAllProperties, "9C6136CB-A9AC-4527-B41A-7A2DB50ACE53")]
1060    public class AllFieldsAndAllPropertiesStorable {
1061      public int Value1 = 1;
1062      [Storable]
1063      public int Value2 = 2;
1064      public int Value3 { get; private set; }
1065      public int Value4 { get; private set; }
1066      [StorableConstructor]
1067      public AllFieldsAndAllPropertiesStorable(bool isDeserializing) {
1068        if (!isDeserializing) {
1069          Value1 = 12;
1070          Value2 = 23;
1071          Value3 = 34;
1072          Value4 = 56;
1073        }
1074      }
1075    }
1076
1077    [TestMethod]
1078    [TestCategory("Persistence")]
1079    [TestProperty("Time", "short")]
1080    public void TestStorableClassDiscoveryAllFieldsAndAllProperties() {
1081      AllFieldsAndAllPropertiesStorable afs = new AllFieldsAndAllPropertiesStorable(false);
1082      XmlGenerator.Serialize(afs, tempFile);
1083      AllFieldsAndAllPropertiesStorable newAfs = (AllFieldsAndAllPropertiesStorable)XmlParser.Deserialize(tempFile);
1084      Assert.AreEqual(afs.Value1, newAfs.Value1);
1085      Assert.AreEqual(afs.Value2, newAfs.Value2);
1086      Assert.AreEqual(afs.Value3, newAfs.Value3);
1087      Assert.AreEqual(afs.Value4, newAfs.Value4);
1088    }
1089
1090    [StorableClass(StorableClassType.MarkedOnly, "75C9F6F0-1B2E-41E7-A327-AF9CF5C87D8D")]
1091    public class MarkedOnlyStorable {
1092      public int Value1 = 1;
1093      [Storable]
1094      public int Value2 = 2;
1095      public int Value3 { get; private set; }
1096      public int Value4 { get; private set; }
1097      [StorableConstructor]
1098      public MarkedOnlyStorable(bool isDeserializing) {
1099        if (!isDeserializing) {
1100          Value1 = 12;
1101          Value2 = 23;
1102          Value3 = 34;
1103          Value4 = 56;
1104        }
1105      }
1106    }
1107
1108    [TestMethod]
1109    [TestCategory("Persistence")]
1110    [TestProperty("Time", "short")]
1111    public void TestStorableClassDiscoveryMarkedOnly() {
1112      MarkedOnlyStorable afs = new MarkedOnlyStorable(false);
1113      XmlGenerator.Serialize(afs, tempFile);
1114      MarkedOnlyStorable newAfs = (MarkedOnlyStorable)XmlParser.Deserialize(tempFile);
1115      Assert.AreEqual(1, newAfs.Value1);
1116      Assert.AreEqual(afs.Value2, newAfs.Value2);
1117      Assert.AreEqual(0, newAfs.Value3);
1118      Assert.AreEqual(0, newAfs.Value4);
1119    }
1120
1121    [TestMethod]
1122    [TestCategory("Persistence")]
1123    [TestProperty("Time", "short")]
1124    public void TestLineEndings() {
1125      List<string> lineBreaks = new List<string> { "\r\n", "\n", "\r", "\n\r", Environment.NewLine };
1126      List<string> lines = new List<string>();
1127      foreach (var br in lineBreaks)
1128        lines.Add("line1" + br + "line2");
1129      XmlGenerator.Serialize(lines, tempFile);
1130      List<string> newLines = XmlParser.Deserialize<List<string>>(tempFile);
1131      Assert.AreEqual(lines.Count, newLines.Count);
1132      for (int i = 0; i < lineBreaks.Count; i++) {
1133        Assert.AreEqual(lines[i], newLines[i]);
1134      }
1135    }
1136
1137    [TestMethod]
1138    [TestCategory("Persistence")]
1139    [TestProperty("Time", "short")]
1140    public void TestSpecialNumbers() {
1141      List<double> specials = new List<double>() { 1.0 / 0, -1.0 / 0, 0.0 / 0 };
1142      Assert.IsTrue(double.IsPositiveInfinity(specials[0]));
1143      Assert.IsTrue(double.IsNegativeInfinity(specials[1]));
1144      Assert.IsTrue(double.IsNaN(specials[2]));
1145      XmlGenerator.Serialize(specials, tempFile);
1146      List<double> newSpecials = XmlParser.Deserialize<List<double>>(tempFile);
1147      Assert.IsTrue(double.IsPositiveInfinity(newSpecials[0]));
1148      Assert.IsTrue(double.IsNegativeInfinity(newSpecials[1]));
1149      Assert.IsTrue(double.IsNaN(newSpecials[2]));
1150    }
1151
1152    [TestMethod]
1153    [TestCategory("Persistence")]
1154    [TestProperty("Time", "short")]
1155    public void TestStringSplit() {
1156      string s = "1.2;2.3;3.4;;;4.9";
1157      var l = s.EnumerateSplit(';').ToList();
1158      Assert.AreEqual("1.2", l[0]);
1159      Assert.AreEqual("2.3", l[1]);
1160      Assert.AreEqual("3.4", l[2]);
1161      Assert.AreEqual("4.9", l[3]);
1162    }
1163
1164    [TestMethod]
1165    [TestCategory("Persistence")]
1166    [TestProperty("Time", "medium")]
1167    public void TestCompactNumberArraySerializer() {
1168      System.Random r = new System.Random();
1169      double[] a = new double[CompactNumberArray2StringSerializer.SPLIT_THRESHOLD * 2 + 1];
1170      for (int i = 0; i < a.Length; i++)
1171        a[i] = r.Next(10);
1172      var config = ConfigurationService.Instance.GetDefaultConfig(new XmlFormat());
1173      config = new Configuration(config.Format,
1174        config.PrimitiveSerializers.Where(s => s.SourceType != typeof(double[])),
1175        config.CompositeSerializers);
1176      XmlGenerator.Serialize(a, tempFile, config);
1177      double[] newA = XmlParser.Deserialize<double[]>(tempFile);
1178      Assert.AreEqual(a.Length, newA.Length);
1179      for (int i = 0; i < a.Rank; i++) {
1180        Assert.AreEqual(a.GetLength(i), newA.GetLength(i));
1181        Assert.AreEqual(a.GetLowerBound(i), newA.GetLowerBound(i));
1182      }
1183      for (int i = 0; i < a.Length; i++) {
1184        Assert.AreEqual(a[i], newA[i]);
1185      }
1186    }
1187    private class IdentityComparer<T> : IEqualityComparer<T> {
1188
1189      public bool Equals(T x, T y) {
1190        return x.Equals(y);
1191      }
1192
1193      public int GetHashCode(T obj) {
1194        return obj.GetHashCode();
1195      }
1196    }
1197
1198    [TestMethod]
1199    [TestCategory("Persistence")]
1200    [TestProperty("Time", "short")]
1201    public void TestHashSetSerializer() {
1202      var hashSets = new List<HashSet<int>>() {
1203        new HashSet<int>(new[] { 1, 2, 3 }),
1204        new HashSet<int>(new[] { 4, 5, 6 }, new IdentityComparer<int>()),
1205      };
1206      XmlGenerator.Serialize(hashSets, tempFile);
1207      var newHashSets = XmlParser.Deserialize<List<HashSet<int>>>(tempFile);
1208      Assert.IsTrue(newHashSets[0].Contains(1));
1209      Assert.IsTrue(newHashSets[0].Contains(2));
1210      Assert.IsTrue(newHashSets[0].Contains(3));
1211      Assert.IsTrue(newHashSets[1].Contains(4));
1212      Assert.IsTrue(newHashSets[1].Contains(5));
1213      Assert.IsTrue(newHashSets[1].Contains(6));
1214      Assert.AreEqual(newHashSets[0].Comparer.GetType(), new HashSet<int>().Comparer.GetType());
1215      Assert.AreEqual(newHashSets[1].Comparer.GetType(), typeof(IdentityComparer<int>));
1216    }
1217
1218    [TestMethod]
1219    [TestCategory("Persistence")]
1220    [TestProperty("Time", "short")]
1221    public void TestConcreteDictionarySerializer() {
1222      var dictionaries = new List<Dictionary<int, int>>() {
1223        new Dictionary<int, int>(),
1224        new Dictionary<int, int>(new IdentityComparer<int>()),
1225      };
1226      dictionaries[0].Add(1, 1);
1227      dictionaries[0].Add(2, 2);
1228      dictionaries[0].Add(3, 3);
1229      dictionaries[1].Add(4, 4);
1230      dictionaries[1].Add(5, 5);
1231      dictionaries[1].Add(6, 6);
1232      XmlGenerator.Serialize(dictionaries, tempFile, ConfigurationService.Instance.GetDefaultConfig(new XmlFormat()));
1233      var newDictionaries = XmlParser.Deserialize<List<Dictionary<int, int>>>(tempFile);
1234      Assert.IsTrue(newDictionaries[0].ContainsKey(1));
1235      Assert.IsTrue(newDictionaries[0].ContainsKey(2));
1236      Assert.IsTrue(newDictionaries[0].ContainsKey(3));
1237      Assert.IsTrue(newDictionaries[1].ContainsKey(4));
1238      Assert.IsTrue(newDictionaries[1].ContainsKey(5));
1239      Assert.IsTrue(newDictionaries[1].ContainsKey(6));
1240      Assert.IsTrue(newDictionaries[0].ContainsValue(1));
1241      Assert.IsTrue(newDictionaries[0].ContainsValue(2));
1242      Assert.IsTrue(newDictionaries[0].ContainsValue(3));
1243      Assert.IsTrue(newDictionaries[1].ContainsValue(4));
1244      Assert.IsTrue(newDictionaries[1].ContainsValue(5));
1245      Assert.IsTrue(newDictionaries[1].ContainsValue(6));
1246      Assert.AreEqual(new Dictionary<int, int>().Comparer.GetType(), newDictionaries[0].Comparer.GetType());
1247      Assert.AreEqual(typeof(IdentityComparer<int>), newDictionaries[1].Comparer.GetType());
1248    }
1249
1250    [StorableClass("A603ABE6-86DB-46F7-AF87-C7B40E4FF169")]
1251    public class ReadOnlyFail {
1252      [Storable]
1253      public string ReadOnly {
1254        get { return "fail"; }
1255      }
1256    }
1257
1258    [TestMethod]
1259    [TestCategory("Persistence")]
1260    [TestProperty("Time", "short")]
1261    public void TestReadOnlyFail() {
1262      try {
1263        XmlGenerator.Serialize(new ReadOnlyFail(), tempFile);
1264        Assert.Fail("Exception expected");
1265      }
1266      catch (PersistenceException) {
1267      }
1268      catch {
1269        Assert.Fail("PersistenceException expected");
1270      }
1271    }
1272
1273
1274    [StorableClass("7EDE1D86-C8F5-4B51-846F-1634C0FE20BB")]
1275    public class WriteOnlyFail {
1276      [Storable]
1277      public string WriteOnly {
1278        set { throw new InvalidOperationException("this property should never be set."); }
1279      }
1280    }
1281
1282    [TestMethod]
1283    [TestCategory("Persistence")]
1284    [TestProperty("Time", "short")]
1285    public void TestWriteOnlyFail() {
1286      try {
1287        XmlGenerator.Serialize(new WriteOnlyFail(), tempFile);
1288        Assert.Fail("Exception expected");
1289      }
1290      catch (PersistenceException) {
1291      }
1292      catch {
1293        Assert.Fail("PersistenceException expected.");
1294      }
1295    }
1296
1297    [StorableClass("65B13830-5D60-4C3F-8D9E-5DCDF1E3A977")]
1298    public class OneWayTest {
1299      public OneWayTest() { this.value = "default"; }
1300      public string value;
1301      [Storable(AllowOneWay = true)]
1302      public string ReadOnly {
1303        get { return "ReadOnly"; }
1304      }
1305      [Storable(AllowOneWay = true)]
1306      public string WriteOnly {
1307        set { this.value = value; }
1308      }
1309    }
1310
1311    [TestMethod]
1312    [TestCategory("Persistence")]
1313    [TestProperty("Time", "short")]
1314    public void TestOneWaySerialization() {
1315      var test = new OneWayTest();
1316      var serializer = new HeuristicLab.Persistence.Core.Serializer(test, ConfigurationService.Instance.GetDefaultConfig(new XmlFormat()));
1317      var it = serializer.GetEnumerator();
1318      it.MoveNext();
1319      Assert.AreEqual("ROOT", ((BeginToken)it.Current).Name); it.MoveNext();
1320      Assert.AreEqual("ReadOnly", ((PrimitiveToken)it.Current).Name); it.MoveNext();
1321      Assert.AreEqual("ROOT", ((EndToken)it.Current).Name); it.MoveNext();
1322      var deserializer = new Deserializer(new[] { 
1323        new TypeMapping(0, typeof(OneWayTest).AssemblyQualifiedName, typeof(StorableSerializer).AssemblyQualifiedName),
1324        new TypeMapping(1, typeof(string).AssemblyQualifiedName, typeof(String2XmlSerializer).AssemblyQualifiedName) });
1325      var newTest = (OneWayTest)deserializer.Deserialize(new ISerializationToken[] {
1326        new BeginToken("ROOT", 0, 0),
1327        new PrimitiveToken("WriteOnly", 1, 1, new XmlString("<![CDATA[serial data]]>")),
1328        new EndToken("ROOT", 0, 0)
1329      });
1330      Assert.AreEqual("serial data", newTest.value);
1331    }
1332
1333    [TestMethod]
1334    [TestCategory("Persistence")]
1335    [TestProperty("Time", "short")]
1336    public void TestTypeCacheExport() {
1337      var test = new List<List<int>>();
1338      test.Add(new List<int>() { 1, 2, 3 });
1339      IEnumerable<Type> types;
1340      using (var stream = new MemoryStream()) {
1341        XmlGenerator.Serialize(test, stream, ConfigurationService.Instance.GetConfiguration(new XmlFormat()), false, out types);
1342      }
1343      List<Type> t = new List<Type>(types);
1344      // Assert.IsTrue(t.Contains(typeof(int))); not serialized as an int list is directly transformed into a string
1345      Assert.IsTrue(t.Contains(typeof(List<int>)));
1346      Assert.IsTrue(t.Contains(typeof(List<List<int>>)));
1347      Assert.AreEqual(t.Count, 2);
1348    }
1349
1350    [TestMethod]
1351    [TestCategory("Persistence")]
1352    [TestProperty("Time", "short")]
1353    public void TupleTest() {
1354      var t1 = Tuple.Create(1);
1355      var t2 = Tuple.Create('1', "2");
1356      var t3 = Tuple.Create(3.0, 3f, 5);
1357      var t4 = Tuple.Create(Tuple.Create(1, 2, 3), Tuple.Create(4, 5, 6), Tuple.Create(8, 9, 10));
1358      var tuple = Tuple.Create(t1, t2, t3, t4);
1359      XmlGenerator.Serialize(tuple, tempFile);
1360      var newTuple = XmlParser.Deserialize<Tuple<Tuple<int>, Tuple<char, string>, Tuple<double, float, int>, Tuple<Tuple<int, int, int>, Tuple<int, int, int>, Tuple<int, int, int>>>>(tempFile);
1361      Assert.AreEqual(tuple, newTuple);
1362    }
1363
1364    [TestMethod]
1365    [TestCategory("Persistence")]
1366    [TestProperty("Time", "short")]
1367    public void FontTest() {
1368      List<Font> fonts = new List<Font>() {
1369        new Font(FontFamily.GenericSansSerif, 12),
1370        new Font("Times New Roman", 21, FontStyle.Bold, GraphicsUnit.Pixel),
1371        new Font("Courier New", 10, FontStyle.Underline, GraphicsUnit.Document),
1372        new Font("Helvetica", 21, FontStyle.Strikeout, GraphicsUnit.Inch, 0, true),
1373      };
1374      XmlGenerator.Serialize(fonts, tempFile);
1375      var newFonts = XmlParser.Deserialize<List<Font>>(tempFile);
1376      Assert.AreEqual(fonts[0], newFonts[0]);
1377      Assert.AreEqual(fonts[1], newFonts[1]);
1378      Assert.AreEqual(fonts[2], newFonts[2]);
1379      Assert.AreEqual(fonts[3], newFonts[3]);
1380    }
1381
1382    [TestMethod]
1383    [TestCategory("Persistence")]
1384    [TestProperty("Time", "medium")]
1385    public void ConcurrencyTest() {
1386      int n = 20;
1387      Task[] tasks = new Task[n];
1388      for (int i = 0; i < n; i++) {
1389        tasks[i] = Task.Factory.StartNew((idx) => {
1390          byte[] data;
1391          using (var stream = new MemoryStream()) {
1392            XmlGenerator.Serialize(new GeneticAlgorithm(), stream);
1393            data = stream.ToArray();
1394          }
1395        }, i);
1396      }
1397      Task.WaitAll(tasks);
1398    }
1399
1400    [TestMethod]
1401    [TestCategory("Persistence")]
1402    [TestProperty("Time", "medium")]
1403    public void ConcurrentBitmapTest() {
1404      Bitmap b = new Bitmap(300, 300);
1405      System.Random r = new System.Random();
1406      for (int x = 0; x < b.Height; x++) {
1407        for (int y = 0; y < b.Width; y++) {
1408          b.SetPixel(x, y, Color.FromArgb(r.Next()));
1409        }
1410      }
1411      Task[] tasks = new Task[20];
1412      byte[][] datas = new byte[tasks.Length][];
1413      for (int i = 0; i < tasks.Length; i++) {
1414        tasks[i] = Task.Factory.StartNew((idx) => {
1415          using (var stream = new MemoryStream()) {
1416            XmlGenerator.Serialize(b, stream);
1417            datas[(int)idx] = stream.ToArray();
1418          }
1419        }, i);
1420      }
1421      Task.WaitAll(tasks);
1422    }
1423
1424    public class G<T, T2> {
1425      public class S { }
1426      public class S2<T3, T4> { }
1427    }
1428
1429    [TestMethod]
1430    [TestCategory("Persistence")]
1431    [TestProperty("Time", "short")]
1432    public void TestInternalClassOfGeneric() {
1433      var s = new G<int, char>.S();
1434      var typeName = s.GetType().AssemblyQualifiedName;
1435      Assert.AreEqual(
1436        "UseCases.G<Int32,Char>.S",
1437        TypeNameParser.Parse(typeName).GetTypeNameInCode(false));
1438      XmlGenerator.Serialize(s, tempFile);
1439      var s1 = XmlParser.Deserialize(tempFile);
1440    }
1441
1442    [TestMethod]
1443    [TestCategory("Persistence")]
1444    [TestProperty("Time", "short")]
1445    public void TestInternalClassOfGeneric2() {
1446      var s = new G<int, float>.S2<int, char>();
1447      var typeName = s.GetType().AssemblyQualifiedName;
1448      Assert.AreEqual(
1449        "UseCases.G<Int32,Single>.S2<Int32,Char>",
1450        TypeNameParser.Parse(typeName).GetTypeNameInCode(false));
1451      XmlGenerator.Serialize(s, tempFile);
1452      var s1 = XmlParser.Deserialize(tempFile);
1453    }
1454
1455    [TestMethod]
1456    [TestCategory("Persistence")]
1457    [TestProperty("Time", "short")]
1458    public void TestSpecialCharacters() {
1459      var s = "abc" + "\x15" + "def";
1460      XmlGenerator.Serialize(s, tempFile);
1461      var newS = XmlParser.Deserialize(tempFile);
1462      Assert.AreEqual(s, newS);
1463    }
1464
1465    [TestMethod]
1466    [TestCategory("Persistence")]
1467    [TestProperty("Time", "short")]
1468    public void TestByteArray() {
1469      var b = new byte[3];
1470      b[0] = 0;
1471      b[1] = 200;
1472      b[2] = byte.MaxValue;
1473      XmlGenerator.Serialize(b, tempFile);
1474      var newB = (byte[])XmlParser.Deserialize(tempFile);
1475      CollectionAssert.AreEqual(b, newB);
1476    }
1477
1478    [TestMethod]
1479    [TestCategory("Persistence")]
1480    [TestProperty("Time", "short")]
1481    public void TestOptionalNumberEnumerable() {
1482      var values = new List<double?> { 0, null, double.NaN, double.PositiveInfinity, double.MaxValue, 1 };
1483      XmlGenerator.Serialize(values, tempFile);
1484      var newValues = (List<double?>)XmlParser.Deserialize(tempFile);
1485      CollectionAssert.AreEqual(values, newValues);
1486    }
1487
1488    [TestMethod]
1489    [TestCategory("Persistence")]
1490    [TestProperty("Time", "short")]
1491    public void TestOptionalDateTimeEnumerable() {
1492      var values = new List<DateTime?> { DateTime.MinValue, null, DateTime.Now, DateTime.Now.Add(TimeSpan.FromDays(1)),
1493        DateTime.ParseExact("10.09.2014 12:21", "dd.MM.yyyy hh:mm", CultureInfo.InvariantCulture), DateTime.MaxValue};
1494      XmlGenerator.Serialize(values, tempFile);
1495      var newValues = (List<DateTime?>)XmlParser.Deserialize(tempFile);
1496      CollectionAssert.AreEqual(values, newValues);
1497    }
1498
1499    [TestMethod]
1500    [TestCategory("Persistence")]
1501    [TestProperty("Time", "short")]
1502    public void TestStringEnumerable() {
1503      var values = new List<string> { "", null, "s", "string", string.Empty, "123", "<![CDATA[nice]]>", "<![CDATA[nasty unterminated" };
1504      XmlGenerator.Serialize(values, tempFile);
1505      var newValues = (List<String>)XmlParser.Deserialize(tempFile);
1506      CollectionAssert.AreEqual(values, newValues);
1507    }
1508
1509    [TestMethod]
1510    [TestCategory("Persistence")]
1511    [TestProperty("Time", "short")]
1512    public void TestUnicodeCharArray() {
1513      var s = Encoding.UTF8.GetChars(new byte[] { 0, 1, 2, 03, 04, 05, 06, 07, 08, 09, 0xa, 0xb });
1514      XmlGenerator.Serialize(s, tempFile);
1515      var newS = (char[])XmlParser.Deserialize(tempFile);
1516      CollectionAssert.AreEqual(s, newS);
1517    }
1518
1519    [TestMethod]
1520    [TestCategory("Persistence")]
1521    [TestProperty("Time", "short")]
1522    public void TestUnicode() {
1523      var s = Encoding.UTF8.GetString(new byte[] { 0, 1, 2, 03, 04, 05, 06, 07, 08, 09, 0xa, 0xb });
1524      XmlGenerator.Serialize(s, tempFile);
1525      var newS = XmlParser.Deserialize(tempFile);
1526      Assert.AreEqual(s, newS);
1527    }
1528
1529    [TestMethod]
1530    [TestCategory("Persistence")]
1531    [TestProperty("Time", "short")]
1532    public void TestQueue() {
1533      var q = new Queue<int>(new[] { 1, 2, 3, 4, 0 });
1534      XmlGenerator.Serialize(q, tempFile);
1535      var newQ = (Queue<int>)XmlParser.Deserialize(tempFile);
1536      CollectionAssert.AreEqual(q, newQ);
1537    }
1538
1539
1540
1541    [ClassInitialize]
1542    public static void Initialize(TestContext testContext) {
1543      ConfigurationService.Instance.Reset();
1544    }
1545  }
1546}
Note: See TracBrowser for help on using the repository browser.