使用可能的不同元素但同一类反序列化XML集合

时间:2016-06-10 06:53:25

标签: c# xml serialization

我正在尝试为Nunit报告分析器/收集器编写类似失败的测试,并且在尝试反序列化测试报告时遇到困难。

Nunit报告有以下结构:

<test-results ... >
    <test-suite>
        <results>
            <test-suite> or <test-case> bunch of elements
                <failure> // optional
        </results>
    </test-suite>
</test-results>

因此,test-suite元素可以使用其他测试套件元素进行结果收集,也可以使用测试用例元素进行结果收集。 由于测试套件具有与测试用例相同的属性,因此可以将其序列化为一个类型类:

[Serializable()]
public class TestResult
{
    [XmlAttribute("name")]
    public String Name { get; set; }
    [XmlAttribute("executed")]
    public String Executed { get; set; }

    [XmlAttribute("success")]
    public String Success { get; set; }

    [XmlElement("failure", IsNullable = true)]
    public Failure Failure { get; set; }

    [XmlElement("results")]
    public Results Results { get; set; }

    [XmlAttribute("result")]
    public String Result { get; set; }

    [XmlAttribute("time")]
    public String Time { get; set; }

    [XmlAttribute("asserts")]
    public String Asserts { get; set; }    
}

[Serializable()]
public class TestCase : TestResult
{

}

[Serializable()]
public class TestSuite : TestResult
{
    [XmlAttribute("type")]
    public String Type { get; set; }
}

结果类假设有一个测试套件或测试用例列表:

[Serializable()]
    public class Results
    {
        [XmlArray("results")]
        [XmlArrayItem("test-case", Type = typeof(TestCase))]
        [XmlArrayItem("test-suite", Type = typeof(TestSuite))]
        public List<Result> Result { get; set; }
    }

这里TestCase和TestSuite是Result的空子类,因为arrtibutes和元素是相同的。从收集中没有以这种方式序列化的项目。如果我正在尝试为每个项目指定多个没有专用类型的ArrauItem-s,那么pardser认为它是不明确的。

我如何实际使用不同但相关的元素进行serialzie收集?

1 个答案:

答案 0 :(得分:1)

我相信下面的结构序列化到你想要的模式(删除非必要属性):

public class TestResult
{
    ...

    [XmlElement("results")]
    public TestResultsCollection Results { get; set; }

    ...
}

public class TestCase : TestResult
{
}

public class TestSuite : TestResult
{
    [XmlAttribute("type")]
    public String Type { get; set; }
}

[XmlRoot("test-results")]
public class TestResultsCollection
{
    [XmlElement("test-case", Type = typeof(TestCase))]
    [XmlElement("test-suite", Type = typeof(TestSuite))]
    public List<TestResult> Results { get; set; }
}

以下是我如何使用它来序列化/反序列化:

var serializer = new XmlSerializer(typeof (TestResultsCollection));

var testResultsCollection = new TestResultsCollection();
testResultsCollection.Items = new List<TestResult>
{
    new TestSuite
    {
        Results = new TestResultsCollection
        {
            Items = new List<TestResult> {new TestCase(), new TestSuite()}
        }
    },
    new TestCase
    {
        Results = new TestResultsCollection
        {
            Items = new List<TestResult> {new TestCase(), new TestSuite()}
        }
    }
};

using (var fileStream = File.CreateText("output.xml"))
{
    serializer.Serialize(fileStream, testResultsCollection);
}

using (var fileStream = File.OpenText("output.xml"))
{
    var deserialized = (TestResultsCollection)serializer.Deserialize(fileStream);
}