Debugging windows services

One problem that I have ran into time and time again while working on windows services is the difficulty around needing to debug them.  Sure, you can setup the service within windows and then start it up and try to attach the debugger before your problem area hits.

But there is a better way. Continue reading

Advertisements

JSON standards vs C# naming standards

Anyone that has coded in C# for any amount of time is accustom to seeing property names in Pascal case such as the example below…

public class MyClass {
    public string MyString { get;set; }
    public int MyInt { get;set; }
}

Which will serialize the class as follows…

{ "MyString":"hello world","MyInt":1 }

Some of your JSON gurus would tell you that the properties for a JSON object should really be in camel case instead of pascal (examples). So we are in-between worlds here trying to find something that will work for everyone.

Our first option would be to use the JsonPropertyAttribute to specify the name for the property during serialization such as below…

public class MyClass {
    [JsonProperty("myString")]
    public string MyString { get;set;}
    [JsonProperty("myInt")]
    public int MyInt { get;set; }
}

Option two would be to make a change in the serialization options such as below…

    MyClass obj = new MyClass()
    {
        MyInt = 1,
        MyString = "hello world";
    };
    var jsonSettings = new JsonSerializerSettings
    {
        ContractResolver = new CamelCasePropertyNamesContractResolver()
    };
    string json = JsonConvert.SerializeObject(obj, Formatting.Indented, jsonSettings);

Both of which will give us our desired output of…

{
  "myString": "hello world",
  "myInt": 1
}

This may be most useful when working within the WebAPI technology of asp.net. If you would like to set the serializer to camelcase for the entire api, you would would need to add the below line to your Application_Start() method within your global.asax

            GlobalConfiguration.Configuration.Formatters.JsonFormatter.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver();

MSTest Headaches. I just need a file!

Last week I was very frustrated trying to get a file to be copied into the running test directory automatically. The test needs to be able to read data from a sample file and then test the logic of the class that would normally parse that file. After a lot of searching, I ended up finding one way to ensure that the file is copied. That is the DeployementItem attribute.

At first glance, I thought it would be easy enough.  Add the attribute to the test method or class, and I’m good to go.  Unfortunately though, it was not quite that easy and what I found is that you also have to change the Copy to Output Directory property of the file in Visual Studio to be Copy always.  After this is done, perform a clean on the test project.  This will insure the file is copied to the bin directory when the test project is compiled.  And then since we have our DeploymentItem attribute set, that will force the file to be copied to the running directory of the test.

using Microsoft.VisualStudio.TestTools.UnitTesting;
using System.Xml;

namespace TestProject1
{
    [TestClass]
    [DeploymentItem("CustomerData.xml")]
    public class UnitTest1
    {
        [TestMethod]
        public void VerifyJohnDoe_Exists()
        {
            XmlDocument xDoc = new XmlDocument();
            xDoc.Load("CustomerData.xml");

            XmlNode johnDoe = xDoc.SelectSingleNode("//Customers/Customer[@name='John Doe']");
            Assert.IsNotNull(johnDoe, "Unable to find the John Doe customer in the data file.");
        }

        [TestMethod]
        public void VerifyDennisDoe_DoesNotExist()
        {
            XmlDocument xDoc = new XmlDocument();
            xDoc.Load("CustomerData.xml");

            XmlNode dennisDoe = xDoc.SelectSingleNode("//Customers/Customer[@name='Dennis Doe']");
            Assert.IsNull(dennisDoe, "Expected result to be null, Dennis Doe does not exist.");
        }
    }
}
<?xml version="1.0"?>
<Customers>
 <Customer name="John Doe" ID="1" />
 <Customer name="Jane Doe" ID="2" />
</Customers>