FridayThe13th the Best JSON Parser for Silverlight and C#/.NET

Up until a couple of months ago I was writing most of my code using WPF. Recently, a project came up where Silverlight made more sense to use. I’d thought that wouldn’t be a problem since I’d just use JavaScriptSerializer [wrote about it here] like I did for my WPF project.

Uh oh. It turns out that Silverlight doesn’t have JavaScriptSerializer. Never fear! DataContractJsonSerializer is here! Or so I thought.

It turns out that if you want to use DataContractJsonSerializer you must actually create POCOs to backup this “data contract.” I didn’t want to do that.

I wanted to turn this…

{
	"some_number": 108.541,
	"date_time": "2011-04-13T15:34:09Z",
	"serial_number": "SN1234"
	"more_data": {
		"field1": 1.0
		"field2": "hello"
	}
}

into..

using System.Web.Script.Serialization;

var jss = new JavaScriptSerializer();
var dict = jss.Deserialize<dynamic>(jsonText);

Console.WriteLine(dict["some_number"]); //outputs 108.541
Console.WriteLine(dict["more_data"]["field2"]); //outputs hello

So I set out to write my own JSON parser. I call it FridayThe13th… how fitting huh? Now, using either Silverlight or .NET 4.0, you can parse the previous JSON into the following:

using FridayThe13th;

var jsonText = File.ReadAllText("mydata.json");

var jsp = new JsonParser(){CamelizeProperties = true};
dynamic json = jsp.Parse(jsonText);

Console.WriteLine(json.SomeNumber); //outputs 108.541
Console.WriteLine(json.MoreData.Field2); //outputs hello

Since I work with a lot of Ruby on Rails backends, I want to add a property “CamelizeProperties” to turn “some_number” into “SomeNumber”… it’s more .NET like.

Try it! You can find it on Github. Oh yeah… it’s also faster than that other .NET JSON library that everyone uses.

Are you a Git user? Let me help you make project management with Git simple. Checkout Gitpilot.

If you made it this far, read my blog on software entrepreneurship and follow me on Twitter: @jprichardson.

-JP

Including More than One ResourceDictionary in Your Xaml

I have one giant Xaml ResourceDictionary that’s becoming unwieldy to manage. The solution is simple. Use MergedDictionaries.

Snippet:

<Window.Resources>
	<ResourceDictionary>
		<ResourceDictionary.MergedDictionaries>
			<ResourceDictionary Source="FileResources1.xaml" />
			<ResourceDictionary Source="FileResources2.xaml" />
		</ResourceDictionary.MergedDictionaries>
	</ResourceDictionary>
</Window.Resources>

Are you a Git user? Let me help you make project management with Git simple. Checkout Gitpilot.

Follow me on Twitter @jprichardson and read my blog on entrepreneurship.

-JP

Convert a CSV to XML using C#

I wrote a simple class that will help you convert a CSV file to XML. I can hear you asking “that’s nice JP, but why would I want to convert my simple CSV to that messy text format from the early 2000’s?” You would do this because you want to use LINQ with CSV files… that’s why.

Here is the crux of the algorithm:

public void Convert() {
	var tempLines = File.ReadAllLines(this.CsvFile);
	string[] lines = null;
	_columnNames = null;
	
	if (this.HasColumnNames) {
		_columnNames = Csv.RecordSplit(tempLines[0], this.RecordDelimiter, this.TextQualifier);
	
		lines = new string[tempLines.Length - 1];
		Array.Copy(tempLines, 1, lines, 0, lines.Length);
	} else {
		var columnCount = Csv.RecordSplit(tempLines[0], this.RecordDelimiter, this.TextQualifier).Length;
		_columnNames = new string[columnCount];
		for (int x = 0; x < _columnNames.Length; ++x)
			_columnNames[x] = "Column" + (x+1);
	
		lines = tempLines;
	}
	
	this.XmlData = new XElement("Records",
		from line in lines
		let fields = Csv.RecordSplit(line, this.RecordDelimiter, this.TextQualifier)
		select new XElement("Record",
			from fieldData in fields
			let i = fields.ToList().FindIndex(f => f == fieldData)
			select new XElement(_columnNames[i], fieldData)
		)
	);
}

You can look at the full code in my C# CommonLib library. As you can see, the code is really straightforward.

Let’s assume that your CSV file looks like this:

'Product','Price','DateStocked'
'Pepsi','4.50','2010-05-04'
'Coke','3.00','2010-09-22'
'Cheetos','7.25','2009-01-13'

You can then run Csv2Xml like this:

var csv = new CsvToXml(csvFile);
csv.RecordDelimiter = ','; 
csv.TextQualifier = '\'';
csv.HasColumnNames = false;
csv.Convert();

var actualXml = csv.XmlString;

The output XML will look like this:

<?xml version="1.0" encoding="utf-8"?>
<Records>
	<Record>
		<Column1>Pepsi</Column1>
		<Column2>4.50</Column2>
		<Column3>2010-05-04</Column3>
	</Record>
	<Record>
		<Column1>Coke</Column1>
		<Column2>3.00</Column2>
		<Column3>2010-09-22</Column3>
	</Record>
	<Record>
		<Column1>Cheetos</Column1>
		<Column2>7.25</Column2>
		<Column3>2009-01-13</Column3>
	</Record>
</Records>

If you set “HasColumnNames” to “True”, your XML output will look like this:

<?xml version="1.0" encoding="utf-8"?>
<Records>
	<Record>
		<Product>Pepsi</Product>
		<Price>4.50</Price>
		<DateStocked>2010-05-04</DateStocked>
	</Record>
	<Record>
		<Product>Coke</Product>
		<Price>3.00</Price>
		<DateStocked>2010-09-22</DateStocked>
	</Record>
	<Record>
		<Product>Cheetos</Product>
		<Price>7.25</Price>
		<DateStocked>2009-01-13</DateStocked>
	</Record>
</Records>

Are you a Git user? Let me help you make project management with Git simple. Checkout Gitpilot.

Pretty nifty huh? In the next post, I’ll explain how you can use this with LINQ. In the mean time follow me on Twitter (@jprichardson) or read my blog on entrepreneurship: Techneur.

-JP