Category: .NET

Fighting with events: Rhino.Mocks strongly typed EventRaiser attempt #2

I just spent good few hours trying to fight awkward limitations of .NET framework in regard to generics, events, delegates and expression trees. And I’m actually not much further than when I started. It bothers me: why put artificial limitations in regard to delegates as generic constraints? I wish I could do:

public IEventManager<T1,T2> Metod<T1,T2,TEvent>(TEvent @event) where TEvent: Func<T1,T2>

(this will not compile, can not use delegates as constraints…) or even better:

public IEventManager<T1,T2> Metod<T1,T2,TEvent>(TEvent @event) where TEvent: void delegate(T1,T2)

This seems to ruin my every idea. Even worse, when I looked for help at Expression Trees, I learned that you can’t have assignments in them, so this will not compile:

public event EventHandler<CancelEventArgs> MyEvent;

 

//somewhere else

Expression<Action<EventHandler<CancelEventArgs>>> exp = x=>MyEvent+=x;

Currently I’m trying to find a way to overcome the fact, that you can’t implicitly cast delegate type to another type with same signature. If I succeed It might be possible to write something roughly similar to:

public class Client

{

    public event EventHandler<CancelEventArgs> MyEvent;

 

    private static void Main(string[] args)

    {

        var repository = new XtoffMockRepository();

        var client = new Client();

        var myEventManager =

            repository.Mock(client.MyEvent);

    }

}

 

public class XtoffMockRepository : MockRepository

{

    public IEventManager<TEvent> Mock<TEvent>(TEvent @event)

    {   ...   }

}

 

public interface IEventManager<T>

{   ...   }

This is however still quite far from what I want to accomplish. In an ideal world, IEventManager<T> would have it’s generic parameter being not TEvent (i.e. EventHandler<CancelEventArgs> in this example) but IEventManager<T1,T2>, where it’s parameters correspond to event method’ parameters (object and CancelEventArgs respectively).

[UPDATE]

As I just noticed I call repository.Mock event inside the class that declares event. This is the only place where passing it as a parameter will work, so this solution will not work either.

Technorati Tags:

Strongly Typed EventRaiser with Rhino.Mocks

I’ve been playing in my limited spare time with Rhino.Mocks, trying to come up with a way to simplify interactions with events, and creating strongly typed IEventRaiser (or something similar). Here’s what I’ve come up with so far:

Strongly typed Rhino.Mocks Event invocation 

It’s not an easy task, but I have few ideas. If you have any ideas or suggestions post them in the comments. I’ll submit it to Ayende, so if he likes it you may actually see this stuff in some future version of Rhino.Mocks.

Technorati Tags:

Framework Tips VIII: Initializing Dictionaries and Collections

In .NET < 3.5 the only collections you could initialize inline were arrays. So this was legal:

public class CollectionTest

{

    public static readonly ICollection<string> _list = 

        new string[]{"one","two","three"};

}

However if you wanted to have List instead of array, you had to use a trick and pass array as constructor parameter:

public static readonly ICollection<string> _list = 

    new List<string>(new string[]{"one","two","three"});

Not the most elegant piece of code, but at least it works. So far so good. What if you wanted to have a IDictionary instead of ICollection? Well… in this case you’re out of luck, at least partially. To have a dictionary initialized, you’d have to use explicit static constructor, and it means – performance hit. Still, it’s better than nothing.

public class CollectionTest

{

    public static readonly IDictionary<string,int> _dictionary = 

        new Dictionary<string,int>();

    static CollectionTest()

    {

        _dictionary.Add("one",1);

        _dictionary.Add("two",2);

        _dictionary.Add("three",3);

    }

}

But this all was in medieval timessmile_wink. Now, with object and collection initializers you can initialize any ICollection, the way you could with Arrays.

private static readonly ICollection<string> _list = 

    new List<string> {"one", "two", "three"};

This is neat, but even better stuff, is that you can do similar thing with Dictionaries, which means, no explicit static constructor required anymore.

private static readonly IDictionary<string, int>

    _data = new Dictionary<string, int>

            {

                {"one", 1},

                {"two", 2},

                {"three", 3}

            }:

Technorati Tags:

Smarties – new productivity plug-in for Visual Studio

I’ve missed it, but two days ago Smarties v1.0 has been released. This is a new productivity plug-in for Visual Studio, with lots of useful refactorings, and strong emphasis on managing #regions. There are quite a few screencasts on the website, so better go and check them out for yourself. The tool is not free, but very reasonably priced, and there’s a trial version. Highly recommended.

Is Subtext project… dead?

I’ve been using Subtext for this blog since its very beginning 10 months ago. Back then I installed what was the latest version (1.9.5 with later security-fix). I was pretty happy with it. I don’t have high needs: it is supported by Windows Live writer, is stable and just works.

opera_errorHowever I’ve been receiving emails from people complaining that they cant post comments to my blog. I checked the issue, and I was able to reproduce it, with error message presented on the screenshot. I googled for it, but I didn’t find out anything useful. I decided to upgrade my blog installation to latest build hoping, that this would fix the issue. Meanwhile I wanted to backup by blog to BlogML, in case something went wrong, and it turned out, that this function is broken as well. I received error message complaining that operation can not be continued, because it couldn’t find some .png image. Anyway, I upgraded to latest 1.9.6 build, but it didn’t fix any of the issues. All it changed, was that now, while exporting to BlogML I get other error, saying that my connection string is wrong. This got me mad, because now I’m tied to Subtext, and there’s no other easy way to migrate to other blog engine without loosing my content.

While I was poking around, looking for solution, I discovered few things. With Phil moving to be the PM of Microsoft’s MVC framework, it looks like Subtext may be a dead project now.

Last Phil’s contribution was 5 months ago, and his last contribution to trunk was 9 months ago (roughly the time he announced he will join Microsoft). There are other contributors as well, but still, the project hasn’t incremented from 1.9.5. to 1.9.6 yet, and it’s been almost a year since last release. Fast look at their build server, reveals yet another issue: there hasn’t been a successful build of Subtext 2.0 for almost 6 months. This all makes me think, that while Phil apparently doesn’t have the time to contribute to the project, it will soon share it predecessor’s (.TEXT) fate.

 

Technorati Tags: ,

Using Extension Methods to make code more readable.

Let’s look at an example:

  diagramThis is somewhat simplified diagram of classes that are part of object model I created for a certain XML format (it doesn’t reflect physical structure of XML file, rather it’s a conceptual, higher level model).

Document can contain few types of elements. To achieve this, it has a method Add, that takes a ValueElement (which is an abstract class).

The problem here, is that it is not obvious what is a ValueElement. You have to know what you can put into Add method, which means, you have to know what ValueElement’s children are. Their names however reflect their other properties, not the fact that they are value elements, which makes it even harder to guess.  You’d have to poke around in the source code to find out.

diagram_document  Why not create Add overload for each value element then? – one might ask, This way IntelliSence would hint us on what are available value elements, would it not?

diagram_code1 Well, it would but it would fix one thing and break few others.

It ties, Document to ValueElement’s hierarchy. This way, every time a new ValueElement’ descendant is added, we would have to change document as well, to add yet another overload to Add.

Why not leave general overload as a catch-all, and add overloads for those descendants we know about?

Well, this is not a good option either. At this point Document doesn’t really care about specific ValueElement. All it needs to know is that it receives a ValueElement. Telling it more, would be telling it too much. Also adding handful of new overloads would bloat the class, and introduce big-class smell.

diagram_extension This is actually one place, where I think Extension Methods would prove useful. I would introduce an extension class, that would keep all specific overloads, calling the only Document’s Add under the cover. This way, Document does not gain any more knowledge about value elements, than it needs to, and users get IntelliSence hints about what they can actually Add to Document.diagram_code2

It could be made even a little bit more verbose, by creating specific methods for each value element, instead of Add’ overloads

public static void AddText(this Document document, Text text)

{ document.Add(text); }

 

public static void AddTranslationUnit(this Document document, TranslationUnit unit)

{ document.Add(unit); }

 

public static void AddUnknownTag(this Document document, UnknownTag tag)

{ document.Add(tag); }

If I was to make a design pattern out of this, I would call it Godfather, partially because I think it’s a cool namesmile_teeth, and partially because DocumentAddExtension (our Godfather class in this example) knowledge about ValueElement’s descendants (its godchildren) and it provides this knowledge to the user, but hides it from the class it’s tied to (Document). Also important thing is, that it’s not part of ValueElement’s inheritance hierarchy (that’s why it’s called Godfather, instead of, ‘Uncle Fred’ or something like thissmile_wink).

ReSharper 4.0 EAP… you said what? January?

January came and went, and much anticipated ReSharper 4.0 Early Access Program is still not available. It seems, that we’ll have to wait another two weeks, before I stop turning off ReSharper every time I want to write something using new C# 3.0 features. What bothers me however is that, although I do understand the vastness of the tool, I’m more and leaning towards agreeing with Alan’s comment on a recent post. C# is getting bigger, .NET is getting bigger, and it looks like JetBrains starts having troubles to keep up. I hope I’m wrong.

Technorati Tags: , , ,

Framework Tips V: Extension Methods and nulls

You can call extension methods on null elements. It’s obvious when you think about it: its a normal static method where you specify its first parameter with this.

using System;

 

namespace ExtensionMethods2

{

    class Program

    {

        static void Main(string[] args)

        {

            string isNull = null;

            Console.WriteLine(isNull.IsNullOrEmpty());

            string isNotNull = "string";

            Console.WriteLine(isNotNull.IsNullOrEmpty());

        }

    }

 

    public static class StringExtensions

    {

        public static bool IsNullOrEmpty(this string s)

        {

            return s == null || s == "";

        }

    }

}

Notice that if it was normal instance method (i.e. defined in the System.String class) I would have to check if my string instance is not null, before calling it, or I would receive runtime NullReferenceException. Now I can move that check to the method, where it belongs, and make my code cleaner. Pretty slick 😉

Framework Tips IV: Check if character exists for given Encoding (CodePage)

In a project I’m currently working on, I needed to check if particular character is a part of given CodePage. Problem with .NET’s Encoding class, is that although it maintains a table mapping Unicode characters to codes in particular CodePage, it keeps it as private field. Moreover it does its best to replace characters it does not contain, with some fallback character.

One might use this fact, and compare character received this way from Encoding’ instance, with original character, assuming, that if they are different, this character is not a part of that CodePage, but this is not an elegant solution. And involves lot of overhead, by first converting char to byte[] and next the other way around.

Another solution is to use an overload of Encoding’s static GetEncoding method, like this:

Encoding.GetEncoding(1252, EncoderFallback.ExceptionFallback, DecoderFallback.ExceptionFallback);

this way, when user tries to convert a character that is not a part of given Encoding’s CharSet, fallback encoder throws an exception. So one might use try/catch and be happy with it, but this too is an awful solution, and also limiting, as you have to create Encoding instance yourself, so you’re helpless in cases when you receive arbitrary encoding.

After little bit of poking around I came up with yet another solution, that seems to be better, faster and more elegant than those two. I however didn’t test it thoroughly so it may have flaws as well (or may not even work at all in some cases). First, let the code speak:

using System;

using System.Text;

 

namespace ConsoleApplication3

{

    public class Program

    {

        static void Main(string[] args)

        {

            char s = '\x015f';  //exists in 1250 but not in 1252

            char a = 'a';       //exists in both

            char t = '\x00fe';  //exists in 1252 but not in 1250

            Encoding ce = Encoding.GetEncoding(1250);

            Encoding we = Encoding.GetEncoding(1252);

            Print(ce, we, s);

            Print(ce, we, a);

            Print(ce, we, t);

            Console.ReadKey();

        }

 

        private static void Print(Encoding ce, Encoding we, char c)

       {

            Console.WriteLine("{0}: {3}: {1,-6} {4}: {2,-6}",

                c, ce.Contains(c), we.Contains(c), ce.WebName, we.WebName);

        }

    }

 

    public static class EncodingExtensions

    {

        public static bool Contains(this Encoding encoding, char character)

        {

            Encoding enc = encoding;

            if (!(enc.EncoderFallback is EncoderFallbackCheckExists) && enc.IsReadOnly)

            {

                //you might want to cache these, in order to avoid having to

                //clone given encoding every time.

                enc = (Encoding)encoding.Clone();

                enc.EncoderFallback = new EncoderFallbackCheckExists();

            }

            int result = enc.GetByteCount(new char[] { character }, 0, 1);

            return result > 0;

 

        }

    }

    

    internal class EncoderFallbackCheckExists:EncoderFallback

    {

        public override int MaxCharCount { get { return 1; } }

 

        public override EncoderFallbackBuffer CreateFallbackBuffer()

        { return new FallbackBufferCheckExists(); }

    }

 

    internal class FallbackBufferCheckExists:EncoderFallbackBuffer

    {

        public override int Remaining { get { return 0; } }

 

        public override bool Fallback(char charUnknown, int index)

        { return false; }

 

        public override bool Fallback(char charUnknownHigh, char charUnknownLow, int index)

        { return false; }

 

        public override char GetNextChar() { return '\0'; }

 

        public override bool MovePrevious() { return false; }

    }

}

I created two classes: one inheriting from EncodierFallback, and one inheriting from EncoderFallbackBuffer. Basically my idea was, that I will provide Encoding instance with fake fallback encoder, that should not try to provide any fallback character. That way Encoding will silently (and fast) fail and its GetBytes and GetByteCount methods will return respectively empty array and 0y.

Only problem I had was to inject actual EncoderFallbackCheckExist instance info Encoding’s EncoderFallback property. Although this property has setter, when IsReadOnly is true, trying to set it, will raise an exception. Encoding however implements ICloneable, and cloning it, does not preserve its readonly state. So after its cloned, you can safely assign its EncoderFallback.

I also created simple EncodingExtensions class, with single extension method, to wrap the whole logic, and attach it to Encoding class, so that you can write:

Encoding encoding = Encoding.GetEncoding(1256);

bool b = encoding.Contains('ź');

Looks good to me, and as far as I’ve checked – works. However if you have better idea how to accomplish this, please leave a comment.

Technorati Tags: , , ,

Framework Tips II: How to get default ANSI Encoding for given culture

It’s sometimes useful to know what is the default ANSI CodePage, for some given culture. It’s quite easy to achieve, thanks to System.Globalization namespace.

CultureInfo cultureInfo = CultureInfo.GetCultureInfo(1252);

Encoding encoding = Encoding.GetEncoding(cultureInfo.TextInfo.ANSICodePage);

However this code will not always work correctly. The problem is, not every culture has default ANSI CodePage, and therefore, for them you’d have to have plan B, like using UTF-8.

CultureInfo cultureInfo = CultureInfo.CurrentUICulture;

int codePage = cultureInfo.TextInfo.ANSICodePage;

Encoding encoding = codePage.Equals(0)?

                        Encoding.UTF8:

                        Encoding.GetEncoding(codePage);

To see, all such cultures, you can use following code:

var cultures = from c in CultureInfo.GetCultures(CultureTypes.AllCultures)

                         where c.TextInfo.ANSICodePage.Equals(0)

                         select c;

foreach (CultureInfo info in cultures)

    Console.WriteLine("{0,-10}{1}", info.Name, info.EnglishName);