/// <summary> Serialization implementation. </summary> public override bool Serialize(XElement elem, object sourceObj, ITypeData expectedType) { if (sourceObj is IEnumerable == false || sourceObj is string) { return(false); } IEnumerable sourceEnumerable = (IEnumerable)sourceObj; Type type = sourceObj.GetType(); Type genericTypeArg = type.GetEnumerableElementType(); if (genericTypeArg.IsNumeric()) { var parser = new NumberFormatter(CultureInfo.InvariantCulture) { UseRanges = false }; elem.Value = parser.FormatRange(sourceEnumerable); return(true); } object prevObj = this.Object; try { this.Object = sourceObj; bool isComponentSettings = sourceObj is ComponentSettings; foreach (object obj in sourceEnumerable) { var step = new XElement(Element); if (obj != null) { type = obj.GetType(); step.Name = TapSerializer.TypeToXmlString(type); if (isComponentSettings) { ComponentSettingsSerializing.Add(obj); } try { Serializer.Serialize(step, obj, expectedType: TypeData.FromType(genericTypeArg)); } finally { if (isComponentSettings) { ComponentSettingsSerializing.Remove(obj); } } } elem.Add(step); } } finally { this.Object = prevObj; } return(true); }
public void InputBasicTests() { var prop = TypeData.FromType(typeof(DelayStep)).GetMember(nameof(DelayStep.DelaySecs)); DelayStep delay = new DelayStep(); Input <double> secs = new Input <double>() { Step = delay, Property = prop }; delay.DelaySecs = 2; Assert.AreEqual(secs.Value, delay.DelaySecs); Input <double> secs2 = new Input <double>() { Step = delay, Property = prop }; Assert.AreEqual(secs, secs2); Input <double> secs3 = new Input <double>() { Step = delay, Property = null }; Input <double> secs4 = new Input <double>() { Step = null, Property = prop }; Input <double> secs5 = new Input <double>() { Step = null, Property = null }; Input <double> secs6 = new Input <double>() { Step = delay, PropertyName = prop.Name }; Assert.IsFalse(secs3 == secs4); Assert.IsFalse(secs4 == secs5); Assert.IsFalse(secs3 == secs5); Assert.IsTrue(secs == secs2); Assert.IsTrue(secs == secs6); { // test serialize var plan = new TestPlan(); plan.ChildTestSteps.Add(delay); plan.ChildTestSteps.Add(new ReadInputStep() { Input = secs }); var planxml = new TapSerializer().SerializeToString(plan); TestPlan plan2 = (TestPlan) new TapSerializer().DeserializeFromString(planxml); var step2 = plan2.ChildTestSteps[1] as ReadInputStep; Assert.IsTrue(step2.Input.Step == plan2.ChildTestSteps[0]); } }
public void ScopeStepTest() { var diag = new DialogStep() { UseTimeout = true }; var diag2 = new DialogStep(); var scope = new SequenceStep(); string parameterName = "Scope\"" + DisplayAttribute.GroupSeparator + "Title"; // name intentionally weird to mess with the serializer. scope.ChildTestSteps.Add(diag); scope.ChildTestSteps.Add(diag2); var member = TypeData.GetTypeData(diag).GetMember("Title"); member.Parameterize(scope, diag, parameterName); member.Parameterize(scope, diag2, parameterName); TypeData.GetTypeData(diag).GetMember("Timeout").Parameterize(scope, diag, "Group\\The Timeout"); var annotation = AnnotationCollection.Annotate(scope); var titleMember = annotation.GetMember(parameterName); titleMember.Get <IStringValueAnnotation>().Value = "New title"; annotation.Write(); Assert.AreEqual("New title", diag.Title); Assert.AreEqual("New title", diag2.Title); var timeoutMember = annotation.GetMember("Group\\The Timeout"); Assert.IsFalse(timeoutMember.Get <IAccessAnnotation>().IsReadOnly); Assert.AreEqual("Group", TypeData.GetTypeData(scope).GetMember("Group\\The Timeout").GetDisplayAttribute().Group[0]); var plan = new TestPlan(); plan.Steps.Add(scope); var str = new TapSerializer().SerializeToString(plan); var plan2 = (TestPlan) new TapSerializer().DeserializeFromString(str); var scope2 = plan2.Steps[0]; var annotation2 = AnnotationCollection.Annotate(scope2); var titleMember2 = annotation2.GetMember(parameterName); Assert.IsNotNull(titleMember2); titleMember2.Get <IStringValueAnnotation>().Value = "New Title 2"; annotation2.Write(); foreach (var step in scope2.ChildTestSteps.Cast <DialogStep>()) { Assert.AreEqual(step.Title, "New Title 2"); } var forwardedMember = (ParameterMemberData)TypeData.GetTypeData(scope2).GetMember(parameterName); Assert.IsNotNull(forwardedMember); member.Unparameterize(forwardedMember, scope2.ChildTestSteps[0]); Assert.IsNotNull(TypeData.GetTypeData(scope2).GetMember(parameterName)); member.Unparameterize(forwardedMember, scope2.ChildTestSteps[1]); Assert.IsNull(TypeData.GetTypeData(scope2).GetMember(parameterName)); // last 'Title' removed. }
public bool Deserialize(XElement node, ITypeData t, Action <object> setter) { if (t.IsA(typeof(Verdict))) { if (node.Value == legacyNotSetName) { node.SetValue(nameof(Verdict.NotSet)); return(TapSerializer.GetCurrentSerializer().Serialize(node, setter, t)); } } if (node.Name == TestStepName && t.DescendsTo(typeof(DialogStep))) { if (currentBox != null) { return(false); } currentBox = new Box(); var serializer = TapSerializer.GetCurrentSerializer(); return(serializer.Deserialize(node, x => { currentBox.Step = (DialogStep)x; setter(x); }, t)); } else if (currentBox != null && node.Name == legacyDefaultAnswerPropertyName) { if (bool.TryParse(node.Value, out bool defaultAnswer)) { node.Remove(); var serializer = TapSerializer.GetCurrentSerializer(); var thisbox = currentBox; serializer.DeferLoad(() => { if (thisbox.Step == null) { return; } if (defaultAnswer) { thisbox.Step.DefaultAnswer = thisbox.Step.PositiveAnswer; } else { thisbox.Step.DefaultAnswer = thisbox.Step.NegativeAnswer; } }); return(true); } } return(false); }
public void VerifyPackageDependencies() { var tp = new TestPlan(); tp.ChildTestSteps.Add(new DelayStep()); var serializer = new TapSerializer(); var str = serializer.SerializeToString(tp); Assert.IsTrue(str.Contains("<Package.Dependencies>")); Assert.IsTrue(serializer.GetUsedTypes().Any(x => x.DescendsTo(TypeData.FromType(typeof(DelayStep))))); }
public void SerializeDeserializeWithDutExternalParameter() { var plan = new TestPlan(); var step = new TestPlanTest.DutStep(); var dut1 = new DummyDut { Name = "DUT1" }; var dut2 = new DummyDut { Name = "DUT2" }; DutSettings.Current.AddRange(new [] { dut1, dut2 }); try { step.Dut = dut1; plan.ChildTestSteps.Add(step); plan.ExternalParameters.Add(step, TypeData.GetTypeData(step).GetMember(nameof(TestPlanTest.DutStep.Dut)), "dut"); using (var memstr = new MemoryStream()) { plan.Save(memstr); var serializer = new TapSerializer(); var ext = serializer.GetSerializer <ExternalParameterSerializer>(); ext.PreloadedValues["dut"] = "DUT2"; memstr.Seek(0, SeekOrigin.Begin); plan = (TestPlan)serializer.Deserialize(memstr); } step = (TestPlanTest.DutStep)plan.ChildTestSteps[0]; Assert.AreEqual(step.Dut, dut2); } finally { DutSettings.Current.Remove(dut1); DutSettings.Current.Remove(dut2); } }
public void MultiLevelScopeSerialization() { var plan = new TestPlan(); var seq1 = new SequenceStep(); var seq2 = new SequenceStep(); var delay = new DelayStep(); plan.ChildTestSteps.Add(seq1); seq1.ChildTestSteps.Add(seq2); seq2.ChildTestSteps.Add(delay); var member1 = TypeData.GetTypeData(delay).GetMember(nameof(DelayStep.DelaySecs)) .Parameterize(seq2, delay, "delay"); member1.Parameterize(seq1, seq2, "delay"); var str = new TapSerializer().SerializeToString(plan); var plan2 = (TestPlan) new TapSerializer().DeserializeFromString(str); var member2 = TypeData.GetTypeData(plan2.ChildTestSteps[0]).GetMember(member1.Name); var val = member2.GetValue(plan2.ChildTestSteps[0]); Assert.AreEqual(delay.DelaySecs, val); }
public bool Deserialize(XElement node, ITypeData t, Action <object> setter) { // 1. 'Iterate and Replace' if the node is the test plan node, we want to find all test step sub-nodes and replace the types. if (t.DescendsTo(typeof(TestPlan))) { iterateAndReplaceTypesInXml(node, node); } else if (node.Attribute(postScaleAttr) is XAttribute attribute) { // 2. do post-scaling. // when the old step was detected the property was marked with this post-scale attribute to show that it should scale it after deserialization. // this is because the old step used milliseconds, but the new one uses seconds. attribute.Remove(); // remove the attribute to avoid hitting this again. // this new setter applies the post-scaling that was added to the attributes during 'iterate and replace'. Action <object> newSetter = x => setter(double.Parse(x.ToString()) * double.Parse(attribute.Value)); // call the deserializer to actually deserialize the property, but direct it to use the new setter instead of the original. return(TapSerializer.GetCurrentSerializer().Deserialize(node, newSetter, t)); } return(false); }
public void SweepLoop2Test() { var plan = new TestPlan(); var sweep = new SweepParameterStep(); var step = new ScopeTestStep(); plan.ChildTestSteps.Add(sweep); sweep.ChildTestSteps.Add(step); sweep.SweepValues.Add(new SweepRow()); sweep.SweepValues.Add(new SweepRow()); TypeData.GetTypeData(step).GetMember(nameof(ScopeTestStep.A)).Parameterize(sweep, step, "Parameters \\ A"); TypeData.GetTypeData(step).GetMember(nameof(ScopeTestStep.EnabledTest)).Parameterize(sweep, step, nameof(ScopeTestStep.EnabledTest)); var td1 = TypeData.GetTypeData(sweep.SweepValues[0]); var memberA = td1.GetMember("Parameters \\ A"); memberA.SetValue(sweep.SweepValues[0], 10); memberA.SetValue(sweep.SweepValues[1], 20); { // verify Enabled<T> works with SweepParameterStep. var annotation = AnnotationCollection.Annotate(sweep); var col = annotation.GetMember(nameof(SweepParameterStep.SelectedParameters)).Get <IStringReadOnlyValueAnnotation>().Value; Assert.AreEqual("A, EnabledTest", col); var elements = annotation.GetMember(nameof(SweepParameterStep.SweepValues)) .Get <ICollectionAnnotation>().AnnotatedElements .Select(elem => elem.GetMember(nameof(ScopeTestStep.EnabledTest))) .ToArray(); annotation.Write(); Assert.IsFalse((bool)elements[0].GetMember("IsEnabled").Get <IObjectValueAnnotation>().Value); elements[0].GetMember("IsEnabled").Get <IObjectValueAnnotation>().Value = true; annotation.Write(); Assert.IsFalse((bool)elements[1].GetMember("IsEnabled").Get <IObjectValueAnnotation>().Value); Assert.IsTrue((bool)elements[0].GetMember("IsEnabled").Get <IObjectValueAnnotation>().Value); } var str = new TapSerializer().SerializeToString(plan); var plan2 = (TestPlan) new TapSerializer().DeserializeFromString(str); var sweep2 = (SweepParameterStep)plan2.Steps[0]; var td2 = TypeData.GetTypeData(sweep2); var members2 = td2.GetMembers(); var rows = sweep2.SweepValues; Assert.AreEqual(2, rows.Count); var msgmem = TypeData.GetTypeData(rows[0]).GetMember("Parameters \\ A"); Assert.AreEqual(10, msgmem.GetValue(rows[0])); // this feature was disabled. //var annotated = AnnotationCollection.Annotate(sweep2); //var messageMember = annotated.GetMember(nameof(ScopeTestStep.A)); //Assert.IsFalse(messageMember.Get<IEnabledAnnotation>().IsEnabled); var run = plan2.Execute(); Assert.AreEqual(Verdict.Pass, run.Verdict); Assert.IsTrue(((ScopeTestStep)sweep2.ChildTestSteps[0]).Collection.SequenceEqual(new[] { 10, 20 })); var name = sweep.GetFormattedName(); Assert.AreEqual("Sweep A, EnabledTest", name); }
private void HandleExternalParametersAndLoadPlan(string planToLoad) { List <string> values = new List <string>(); var serializer = new TapSerializer(); var extparams = serializer.GetSerializer <Plugins.ExternalParameterSerializer>(); if (External.Length > 0) { values.AddRange(External); } if (TryExternal.Length > 0) { values.AddRange(TryExternal); } Plan = new TestPlan(); List <string> externalParameterFiles = new List <string>(); foreach (var externalParam in values) { int equalIdx = externalParam.IndexOf('='); if (equalIdx == -1) { externalParameterFiles.Add(externalParam); continue; } var name = externalParam.Substring(0, equalIdx); var value = externalParam.Substring(equalIdx + 1); extparams.PreloadedValues[name] = value; } var log = Log.CreateSource("CLI"); var timer = Stopwatch.StartNew(); using (var fs = new FileStream(planToLoad, FileMode.Open, FileAccess.Read)) { // only cache the XML if there are no external parameters. bool cacheXml = values.Any() == false && externalParameterFiles.Any() == false; Plan = TestPlan.Load(fs, planToLoad, cacheXml, serializer, IgnoreLoadErrors); log.Info(timer, "Loaded test plan from {0}", planToLoad); } if (externalParameterFiles.Count > 0) { var importers = CreateInstances <IExternalTestPlanParameterImport>(); foreach (var file in externalParameterFiles) { var ext = Path.GetExtension(file); log.Info($"Loading external parameters from '{file}'."); var importer = importers.FirstOrDefault(i => i.Extension == ext); if (importer != null) { importer.ImportExternalParameters(Plan, file); } else { log.Error($"No installed plugins provide loading of external parameters from '{ext}' files. No external parameters loaded from '{file}'."); } } } if (External.Length > 0) { // Print warnings if an --external parameter was not in the test plan. foreach (var externalParam in External) { var equalIdx = externalParam.IndexOf('='); if (equalIdx == -1) { continue; } var name = externalParam.Substring(0, equalIdx); if (Plan.ExternalParameters.Get(name) != null) { continue; } log.Warning("External parameter '{0}' does not exist in the test plan.", name); log.Warning("Statement '{0}' has no effect.", externalParam); throw new ArgumentException(""); } } }