I've been setting up a Cake script (C# Make) in preparation of automating our unit testing. I have the script set up and it's running the unit tests as expected except for one quirk...
One of the simpler tests is failing when MSTest attempts to execute it but it passes with flying colors when I run the test from VS 2013.
[TestMethod]
public void Field_is_XmlNode_innertext_urlencode()
{
// Arrange
var xmlDoc = new XmlDocument();
xmlDoc.LoadXml("<field>\"'#</field>");
var fetchedField = xmlDoc.SelectSingleNode("field");
// Assert
Assert.AreEqual("%22%27%23", CrmHelpers.GetFetchedFieldValueAsString(fetchedField, null, true));
}
Cake script section that calls MSTest.
Task("RunTests")
.IsDependentOn("Build")
.Does(() =>
{
Information("TestPath {0}", "./Tests/Unit Tests/**/bin/" + configuration + "/*.UnitTests.dll");
MSTest("./Tests/Unit Tests/**/bin/" + configuration + "/*.UnitTests.dll");
});
In VS2013 the value \"'# is properly encoded to %22%27%23 however when executing the test via Cake calling MSTest that same value is encoded as %22'%23.
My questions are: Why are these values encoded differently in MSTest from what I see in VS2013 when theoretically it should be running the same code? How do I correct the issue so that MSTest runs all of my unit tests in a predictable and consistent manner?
EDIT 1: Adding requested method
public static string GetFetchedFieldValueAsString(XmlNode fetchedField, string format, bool urlEncode)
{
var fieldValue = "";
if (format.IsNotEmpty())
{
try
{
if (fetchedField.Attributes["date"] != null)
{
var date = DateTime.Parse(fetchedField.InnerText).ToUniversalTime();
fieldValue = GetFormatedDateAsString(date, format);
}
else if (fetchedField.InnerText.IsNumeric())
{
var number = float.Parse(fetchedField.InnerText);
fieldValue = number.ToString(format);
}
}
catch
{
// Ignore formating errors
}
}
if (fieldValue.IsEmpty()) fieldValue = fetchedField.GetAttributeValue("name");
if (fieldValue.IsEmpty()) fieldValue = fetchedField.GetAttributeValue("formattedvalue");
if (fieldValue.IsEmpty() && fetchedField.Attributes["date"] != null)
{
var date = fetchedField.GetAttributeValue("date");
var time = fetchedField.GetAttributeValue("time");
if (date.IsNotEmpty()) fieldValue = date;
if (date.IsNotEmpty() && time.IsNotEmpty()) fieldValue += " ";
if (time.IsNotEmpty()) fieldValue += time;
}
if (fieldValue.IsEmpty()) fieldValue = fetchedField.InnerText;
if (fieldValue.IsGuid()) fieldValue = fieldValue.Replace("{", "").Replace("}", "");
fieldValue = fieldValue.Sanitize();
if (urlEncode) fieldValue = fieldValue.UrlComponentEncode();
return fieldValue;
}
EDIT 2: Adding requested method
public static string UrlComponentEncode(this string s)
{
return Uri.EscapeDataString(s);
}
EDIT 3: Cake Methods to get MSTest path
/// <summary>
/// Gets the default tool path.
/// </summary>
/// <returns>The default tool path.</returns>
protected override FilePath GetDefaultToolPath(MSTestSettings settings)
{
foreach (var version in new[] { "12.0", "11.0", "10.0" })
{
var path = GetToolPath(version);
if (_fileSystem.Exist(path))
{
return path;
}
}
return null;
}
private FilePath GetToolPath(string version)
{
var programFiles = _environment.GetSpecialPath(SpecialPath.ProgramFilesX86);
var root = programFiles.Combine(string.Concat("Microsoft Visual Studio ", version, "/Common7/IDE"));
return root.CombineWithFilePath("mstest.exe");
}