A gentle reminder that interfaces aren't contracts

I received a gentle reminder this evening that interfaces aren’t contracts. I was attempting to bend Silverlight 2 to my will, specifically the ResourceDictionary. I really wanted the keys, and was pleased to see that it implemented IDictionary<object,object>, which would give me a collection of keys (of object). I was dismayed to see the following implementation in reflector for the Keys and Values properties.

    ICollection<object> IDictionary<object, object>.Keys
    {
        get { throw new NotImplementedException(); }
    }

    ICollection<object> IDictionary<object, object>.Values
    {
        get { throw new NotImplementedException(); }
    }

This really brought home to me that Interfaces are nice and all, but really only tell us that a type will have methods with a certain name that take certain paramters - exactly the same thing the compiler tells us about lots of other things (that is if you’re in a compiled world….the benefits of interfaces seem even more marginal in more dynamically typed duck typing* languages). It doesn’t guarantee that the methods will actually DO what we think they’ll do (or even that they’ll do anything at all except throw an exception in your face). Don’t get me wrong - I like and user interfaces, but they’re not a contract, more of a gentleman’s agreement or shared understanding. Now if you’ll excuse me I have some nasty reflection hacks I need to brutally force on the Silverlight run-time.

* Aside: speaking of duck typing, I heard of another interesting turn of phrase for monkey patching - duck punching! If it walks like a duck and flaps like a duck but doesn’t quite quack the way you want it to you just punch it [chewie].

 

Comments

Riaz
Been googling this early morning as I’m also trying to bend the rules with Silverlight 2!

See, I’m having to convert a WPF project to Silverlight 2 and am having an absolute nightmare to come to terms with the much limited Resources in Silverlight (no merge etc).

The furthest I got was:
1) Keep the styling as a ResourceDictionary as an XML data type in SQL Server
2) Pull the data via WCF to a string
3) Load the string via XamlReader.Load in Silverlight and cast as ResourceDictionary

So far, so good. I have a working ResourceDictionary object and all x:Key defined in it.

As Application.Current.Resources is read-only (unlike WPF), can’t simply stick the dynamicly rendered resource dictionary to it.

Can’t also simply do Application.Current.Resources.Add(the_loaded_resource).
The keys don’t get added for some reason.

What I CAN do is:
foreach (DependencyObject d in the_loaded_resource)
{
Application.Current.Resources.Add(d);
}

The problem with the above approach is that ’d’ gets added without it’s ‘key’ setting. So while the styles/brushes/etc are added to the Application’s resource dictionary, the keys are lost.

To make things work, I have to manually type the key. Hence
Application.Curent.Resources.Add("HardCodedKey",d);

Which leads to your post. How on earth do I list the keys in the loaded resource dictionary to get all the names and not having to add them via hard coding?

Pls let me know if you find a way round it!
24/04/2008 8:12:00 AM
lb
This is why everyone should be using Spec#.

Real contracts at interface boundaries.
15/05/2008 5:21:00 AM