2010-06-21 Atsushi Enomoto <atsushi@ximian.com>
[mcs.git] / nunit24 / ClientUtilities / util / XmlResultVisitor.cs
blob4714a360c46343ba88e4a2af7937476e35bbd302
1 // ****************************************************************
2 // This is free software licensed under the NUnit license. You
3 // may obtain a copy of the license as well as information regarding
4 // copyright ownership at http://nunit.org/?p=license&r=2.4.
5 // ****************************************************************
7 namespace NUnit.Util
9 using System;
10 using System.Globalization;
11 using System.IO;
12 using System.Xml;
13 using System.Reflection;
14 using NUnit.Core;
16 /// <summary>
17 /// Summary description for XmlResultVisitor.
18 /// </summary>
19 public class XmlResultVisitor : ResultVisitor
21 private XmlTextWriter xmlWriter;
22 private TextWriter writer;
23 private MemoryStream memoryStream;
25 public XmlResultVisitor(string fileName, TestResult result)
27 xmlWriter = new XmlTextWriter( new StreamWriter(fileName, false, System.Text.Encoding.UTF8) );
28 Initialize(result);
31 public XmlResultVisitor( TextWriter writer, TestResult result )
33 this.memoryStream = new MemoryStream();
34 this.writer = writer;
35 this.xmlWriter = new XmlTextWriter( new StreamWriter( memoryStream, System.Text.Encoding.UTF8 ) );
36 Initialize( result );
39 private void Initialize(TestResult result)
41 ResultSummarizer summaryResults = new ResultSummarizer(result);
43 xmlWriter.Formatting = Formatting.Indented;
44 xmlWriter.WriteStartDocument(false);
45 xmlWriter.WriteComment("This file represents the results of running a test suite");
47 xmlWriter.WriteStartElement("test-results");
49 xmlWriter.WriteAttributeString("name", summaryResults.Name);
50 xmlWriter.WriteAttributeString("total", summaryResults.ResultCount.ToString());
51 xmlWriter.WriteAttributeString("failures", summaryResults.FailureCount.ToString());
52 xmlWriter.WriteAttributeString("not-run", summaryResults.TestsNotRun.ToString());
54 DateTime now = DateTime.Now;
55 xmlWriter.WriteAttributeString("date", XmlConvert.ToString( now, "yyyy-MM-dd" ) );
56 xmlWriter.WriteAttributeString("time", XmlConvert.ToString( now, "HH:mm:ss" ));
57 WriteEnvironment();
58 WriteCultureInfo();
61 private void WriteCultureInfo() {
62 xmlWriter.WriteStartElement("culture-info");
63 xmlWriter.WriteAttributeString("current-culture",
64 CultureInfo.CurrentCulture.ToString());
65 xmlWriter.WriteAttributeString("current-uiculture",
66 CultureInfo.CurrentUICulture.ToString());
67 xmlWriter.WriteEndElement();
70 private void WriteEnvironment() {
71 xmlWriter.WriteStartElement("environment");
72 xmlWriter.WriteAttributeString("nunit-version",
73 Assembly.GetExecutingAssembly().GetName().Version.ToString());
74 xmlWriter.WriteAttributeString("clr-version",
75 Environment.Version.ToString());
76 xmlWriter.WriteAttributeString("os-version",
77 Environment.OSVersion.ToString());
78 xmlWriter.WriteAttributeString("platform",
79 Environment.OSVersion.Platform.ToString());
80 xmlWriter.WriteAttributeString("cwd",
81 Environment.CurrentDirectory);
82 xmlWriter.WriteAttributeString("machine-name",
83 Environment.MachineName);
84 xmlWriter.WriteAttributeString("user",
85 Environment.UserName);
86 xmlWriter.WriteAttributeString("user-domain",
87 Environment.UserDomainName);
88 xmlWriter.WriteEndElement();
91 public void Visit(TestCaseResult caseResult)
93 xmlWriter.WriteStartElement("test-case");
94 xmlWriter.WriteAttributeString("name",caseResult.Name);
96 if(caseResult.Description != null)
97 xmlWriter.WriteAttributeString("description", caseResult.Description);
99 xmlWriter.WriteAttributeString("executed", caseResult.Executed.ToString());
100 if(caseResult.Executed)
102 xmlWriter.WriteAttributeString("success", caseResult.IsSuccess.ToString() );
104 xmlWriter.WriteAttributeString("time", caseResult.Time.ToString("#####0.000", NumberFormatInfo.InvariantInfo));
106 xmlWriter.WriteAttributeString("asserts", caseResult.AssertCount.ToString() );
107 WriteCategories(caseResult);
108 WriteProperties(caseResult);
109 if(caseResult.IsFailure)
111 if(caseResult.IsFailure)
112 xmlWriter.WriteStartElement("failure");
113 else
114 xmlWriter.WriteStartElement("error");
116 xmlWriter.WriteStartElement("message");
117 xmlWriter.WriteCData( EncodeCData( caseResult.Message ) );
118 xmlWriter.WriteEndElement();
120 xmlWriter.WriteStartElement("stack-trace");
121 if(caseResult.StackTrace != null)
122 xmlWriter.WriteCData( EncodeCData( StackTraceFilter.Filter( caseResult.StackTrace ) ) );
123 xmlWriter.WriteEndElement();
125 xmlWriter.WriteEndElement();
129 else
131 WriteCategories(caseResult);
132 WriteProperties(caseResult);
133 xmlWriter.WriteStartElement("reason");
134 xmlWriter.WriteStartElement("message");
135 xmlWriter.WriteCData(caseResult.Message);
136 xmlWriter.WriteEndElement();
137 xmlWriter.WriteEndElement();
140 xmlWriter.WriteEndElement();
143 /// <summary>
144 /// Makes string safe for xml parsing, replacing control chars with '?'
145 /// </summary>
146 /// <param name="encodedString">string to make safe</param>
147 /// <returns>xml safe string</returns>
148 private static string CharacterSafeString(string encodedString)
150 /*The default code page for the system will be used.
151 Since all code pages use the same lower 128 bytes, this should be sufficient
152 for finding uprintable control characters that make the xslt processor error.
153 We use characters encoded by the default code page to avoid mistaking bytes as
154 individual characters on non-latin code pages.*/
155 char[] encodedChars = System.Text.Encoding.Default.GetChars(System.Text.Encoding.Default.GetBytes(encodedString));
157 System.Collections.ArrayList pos = new System.Collections.ArrayList();
158 for(int x = 0 ; x < encodedChars.Length ; x++)
160 char currentChar = encodedChars[x];
161 //unprintable characters are below 0x20 in Unicode tables
162 //some control characters are acceptable. (carriage return 0x0D, line feed 0x0A, horizontal tab 0x09)
163 if(currentChar < 32 && (currentChar != 9 && currentChar != 10 && currentChar != 13))
165 //save the array index for later replacement.
166 pos.Add(x);
169 foreach(int index in pos)
171 encodedChars[index] = '?';//replace unprintable control characters with ?(3F)
173 return System.Text.Encoding.Default.GetString(System.Text.Encoding.Default.GetBytes(encodedChars));
176 private string EncodeCData( string text )
178 return CharacterSafeString( text ).Replace( "]]>", "]]&gt;" );
181 public void WriteCategories(TestResult result)
183 if (result.Test.Categories != null && result.Test.Categories.Count > 0)
185 xmlWriter.WriteStartElement("categories");
186 foreach (string category in result.Test.Categories)
188 xmlWriter.WriteStartElement("category");
189 xmlWriter.WriteAttributeString("name", category);
190 xmlWriter.WriteEndElement();
192 xmlWriter.WriteEndElement();
196 public void WriteProperties(TestResult result)
198 if (result.Test.Properties != null && result.Test.Properties.Count > 0)
200 xmlWriter.WriteStartElement("properties");
201 foreach (string key in result.Test.Properties.Keys)
203 xmlWriter.WriteStartElement("property");
204 xmlWriter.WriteAttributeString("name", key);
205 xmlWriter.WriteAttributeString("value", result.Test.Properties[key].ToString() );
206 xmlWriter.WriteEndElement();
208 xmlWriter.WriteEndElement();
212 public void Visit(TestSuiteResult suiteResult)
214 xmlWriter.WriteStartElement("test-suite");
215 xmlWriter.WriteAttributeString("name",suiteResult.Name);
216 if(suiteResult.Description != null)
217 xmlWriter.WriteAttributeString("description", suiteResult.Description);
219 xmlWriter.WriteAttributeString("success", suiteResult.IsSuccess.ToString());
220 xmlWriter.WriteAttributeString("time", suiteResult.Time.ToString("#####0.000", NumberFormatInfo.InvariantInfo));
221 xmlWriter.WriteAttributeString("asserts", suiteResult.AssertCount.ToString() );
223 WriteCategories(suiteResult);
224 WriteProperties(suiteResult);
226 if ( suiteResult.IsFailure && suiteResult.FailureSite == FailureSite.SetUp )
228 xmlWriter.WriteStartElement("failure");
230 xmlWriter.WriteStartElement("message");
231 xmlWriter.WriteCData( EncodeCData( suiteResult.Message ) );
232 xmlWriter.WriteEndElement();
234 xmlWriter.WriteStartElement("stack-trace");
235 if(suiteResult.StackTrace != null)
236 xmlWriter.WriteCData( EncodeCData( StackTraceFilter.Filter( suiteResult.StackTrace ) ) );
237 xmlWriter.WriteEndElement();
239 xmlWriter.WriteEndElement();
242 xmlWriter.WriteStartElement("results");
243 foreach (TestResult result in suiteResult.Results)
245 result.Accept(this);
247 xmlWriter.WriteEndElement();
249 xmlWriter.WriteEndElement();
252 public void Write()
254 try
256 xmlWriter.WriteEndElement();
257 xmlWriter.WriteEndDocument();
258 xmlWriter.Flush();
260 if ( memoryStream != null && writer != null )
262 memoryStream.Position = 0;
263 using ( StreamReader rdr = new StreamReader( memoryStream ) )
265 writer.Write( rdr.ReadToEnd() );
269 xmlWriter.Close();
271 finally
273 //writer.Close();