Nullable Types and ADO.NET don't like each other

Hopefully this will quickly be proven to be out of date, but at least as of the June CTP of C# 2.0, nullable types are not welcome by SqlParameter objects. This strikes me as extremely odd. Personally, I thought the whole reason to add nullable types to C# 2.0 is to finally get rid of the Value Type/Database Type disconnect over null values.

The biggest frustration building type-safe database interfaces has always been that value types cannot be null, but any column in a database can be null. I should stop here and also point out that 99% of the time columns in database are marked as "allow null" when they shouldn't. A column should only allow null if that null has a special meaning. Half the time people just use null to mean 0 for ints and then you get a lovely mix of 0 and null in there that means the same to business logic, but you have to treat watch out for when you run your reports against that table. Don't use null, unless you mean it! But I digress...

Type-safe database interfaces want to pull datatypes from the DB as their native types. So an int in the DB shoud be an int in code. But what do you do when that int allows null, to mark an unset value for example? Do you create a magic number like 0 that means null? Do you store it as object internally after all and throw exceptions when someone tries to access the null value? None of the solutions are all that appetizing.

Then C# 2.0 introduced nullable types. Value types that could have a null value. Yay, the disconnect has been plugged! Or so I should until i tried executing my first SqlCommand that had an SqlParameter with a nullable int passed in. It promptly threw an invalid cast exception.

So for the time being, at least, I get to do a fun little dance of checking for is INullableValue and then casting the value to INullableValue so I can check HasValue and use Value to get the underlying type. We'll see what happens with the release version of Visual Studio 2005 in December.