StyleCop v4.3 now available

StyleCop version 4.3 was released last tuesday. A short summary of what version 4.3 brings us: 

  • Various bugfixes, including fixes for VS integration issues
  • Rules documentation is included and integrated into VS “Show Error Help”
  • New rules, see blogpost for the rules
  • Branding change from Source Analysis to StyleCop

    Links
    StyleCop blog: http://blogs.msdn.com/sourceanalysis/
    Release announcement on the StyleCop blog: http://blogs.msdn.com/sourceanalysis/archive/2008/08/19/stylecop-4-3-is-released.aspx
    StyleCop 4.3 download: http://code.msdn.microsoft.com/Release/ProjectReleases.aspx?ProjectName=sourceanalysis&ReleaseId=1425

  • Cool tool: DebugView

    Taken from the SysInternals website:

    The SysInternals web site was created in 1996 by Mark Russinovich and Bryce Cogswell to host their advanced system utilities and technical information. Microsoft acquired Sysinternals in July, 2006. Whether you’re an IT Pro or a developer, you’ll find Sysinternals utilities to help you manage, troubleshoot and diagnose your Windows systems and applications.

    One of the must-have SysInternals tools for a developer is DebugView.

    DebugView is an application that lets you monitor debug output on your local system, or any computer on the network that you can reach via TCP/IP. It is capable of displaying both kernel-mode and Win32 debug output, so you don’t need a debugger to catch the debug output your applications or device drivers generate, nor do you need to modify your applications or drivers to use non-standard debug output APIs.

    So that means that an easy Debug.Write (or Debug.WriteLine) statement is picked up by the DebugView tool, and displayed in the tool. From there, you can filter the lines, search them and more…!
    The code that made this screenshot: Debug.WriteLine(“Written through a simple Debug.WriteLine statement”);

    DebugViewScreenshot

    Technorati tags: ,,

    Microsoft Research: Sphere multi-touch computing

    Earlier this week the Microsoft Research Faculty Summit was held. On 10 was on the scene, and has a nice movie about the Sphere. For the entire article @ on 10, have a look over here: http://on10.net/blogs/laura/Sphere-multi-touch-computing/.

    This is just another sign that the best is yet to come… Good times :)

    A new view on Microsoft, Google, Apple and Linux

    Rob Enderle, columnist at TechNewsWorld, gives a new/changed view on Microsoft, Google, Apple and Linux in his article The Fall of Google, the Rebirth of Microsoft and the Changing Face of Apple and Linux. A nice read…

    One of the cool quotes from the article:

    …but it becomes risky for anyone to depend on the other guy screwing up as they typically don’t forever.

    By |July 23rd, 2008|Link|0 Comments

    New Avanade NL website online

    Avanade Netherlands released a new website [1]. Unlike the previous one, this one is here to stay ;)
    The website holds information about events, career possibilities, publications, videos, links to blogs of Avanade Netherlands employees and more… Have a look!

    It is in Dutch, by the way.

    [1] http://www.werkenbijavanade.nl (Dutch)

    Technorati tags: ,
    By |July 3rd, 2008|Link|1 Comment

    Running code analysis on a custom stsadm command gives errors CA0052 and CA0055

    When you want to implement a custom stsadm for SharePoint, all you realy have to do is implement the Microsoft.SharePoint.StsAdmin.ISPStsadmCommand interface. Because I develop on a machine with no SharePoint installed, I (only) copy the assemblies I need to develop locally. For the stsadm command I was working on recently (more on this in a future post) I only needed the Microsoft.SharePoint and Microsoft.Office.Server assemblies. Or at least I thought so…

    After implementing the functionality I tried running code analysis, and I got two errors:

    CA0052 : No targets were selected.
    CA0055 : Could not load AssemblyName.

    After trying several ways to fix this, I finally compiled the project on a machine with SharePoint installed. At that point, compiling and running code analysis both worked fine. Code analysis then gave a warning that pointed me to the solution of the problem:

    CA2123 : Microsoft.Security : Add the following security attribute to ‘ClassName.MethodName(string)’ in order to match a LinkDemand on base method ‘ISPStsadmCommand.GetHelpMessage(string)’:  [SharePointPermission(SecurityAction.LinkDemand, ObjectModel = true)].

    Apparently the attribute requires an extra reference. When I copied that assembly (Microsoft.SharePoint.Security) to my non-SharePoint development machine, all worked correctly. FYI: I did add the attribute code analysis suggested by the way.

    A not so clear Visual Studio code analysis message (CA1308)

    While writing a custom stsadm command for SharePoint (more on that in a future post) and having to do something based on the command the user typed in, I used ToLower(CultureInfo.InvariantCulture) on the command string to be able to check without the hassle of differences in casing. When I ran code analysis on my project, I got this somewhat cryptic message:

    CA1308 : Microsoft.Globalization : In method ‘CommandParser.Run(string, StringDictionary, out string)’, replace the call to ‘string.ToLower(CultureInfo)’ with String.ToUpperInvariant().

    So in order to solve a code analysis warning I should change lowercasing a string to a call to ToUpperInvariant? That seems a bit strange, right? Because I was almost sure this could not be a typo, I searched around a bit. When you search for the error number, you get an explanation from Microsoft through the MSDN article Normalize strings to uppercase [1]. Apparently there’s an issue with a small group of characters which are unable to round trip when converted to lowercase. For more information: have a look at Michael Kaplan’s post Get off my (lower) case! (or: Casing, the 1st) which explains it pretty well [2].

    Hope this helps some of you ;)

    [1] http://msdn.microsoft.com/en-us/library/bb386042.aspx
    [2] http://blogs.msdn.com/michkap/archive/2004/12/02/273619.aspx

    The absolute minimum every software developer …

    One of the posts that is being read quite frequently over here is HOWTO: Encode a password using MD5 in C# (or: howto calculate the MD5 hash for a string). One of the (many) reactions to that post was from one Simucal, stating:

    Also, to the original poster, Rick van den Bosch… shame on you for using ASCIIEncoding.Default.GetBytes().  You do realize that would seriously restrict the usefulness of your method to working only in languages that ASCII has the character sets for, right?

    I suggest you read this article entitled:

    The Absolute Minimum Every Software Developer Absolutely, Positively Must Know About Unicode and Character Sets (No Excuses!)

    Yes, I do realize that using ASCIIEncoding.Default.GetBytes() would seriously restrict the usefulness of the method to working only in languages that ASCII has the character sets for. The primary reason for the post was to illustrate the way to calculate the hash. Representing it as a string was only there to be complete for a specific scenario. I did not try to write a hashing function for every language ;)

    That being said, the post Simucal refers to is a good one, and it truly is the absolute minimum every software developer absolutely, positively must know about unicode and character sets. And I guess there are no excuses ;). So if you haven’t done so already, go and read it.

    By |June 11th, 2008|.Net, Blog, HowTo|0 Comments

    A scenario where LINQ is too dynamic (answered)

    The situation I talked about in my previous post had one very big issue: LINQ sometimes just is too dynamic… ;)
    The fact that I changed the value for the Ranking property for each SpecificObject that got matched, made the primary LINQ query have a different outcome. LINQ uses lazy evaluation and  because of that, the contents of finalGroups and exitGroups changed every time I changed the Ranking value for one of the SpecificObjects. Each time the variable containing the outcome of the LINQ query is iterated through, the query is evaluated again. This made that the matching was all off, and I ended up with a bunch of exit groups that got matched!

    To have a simple solution, I did the following. This holds the final and exit objects in a ‘static’ list in stead of a dynamic query result. This way, the SpecificObjects in the finalObjects and exitObjects lists stay the same, regardless of the changes you make to any of the SpecificObjects.

    int count;
    int numberOfPossibilities;
    IEnumerable<SpecificObject> temp;
    List<SpecificObject> finalObjects;
    List<SpecificObject> exitObjects;

    count = 0;
    finalObjects = new List<SpecificObject>();
    exitObjects = new List<SpecificObject>();

    temp = from SpecificObject specificObject in AllSpecificObjects
           orderby specificObject.Ranking
           select specificObject;

    foreach (SpecificObject specificObject in temp)
    {
        if (count < numberOfPossibilities)
        {
            finalObjects.Add(specificObject);
        }
        else
        {
            exitObjects.Add(specificObject);
        }
        count++;
    }

    By the way, we have a winner. Ruud Campsteijn was pretty quick with the right answer!

    By |June 7th, 2008|.Net, Linq|0 Comments

    A scenario where LINQ is too dynamic

    While developing an algorithm to match preferences to possibilities, I had to sort a generic list of a specific object type (SpecificObject). The first x objects would be matched, the rest would be excluded because of the number of available places. To determine the group of objects that would be matched and the group that would be excluded, I did something like this:

    IEnumerable<SpecificObject> sortedObjects;
    IEnumerable<SpecificObject> finalObjects;
    IEnumerable<SpecificObject> exitObjects;

    sortedObjects = from SpecificObject specificObject in AllSpecificObjects
                    orderby specificObject.Ranking
                    select specificObject;

    finalObjects = sortedObjects.Take<SpecificObject>(numberOfPossibilities);
    exitObjects = sortedObjects.Skip<SpecificObject>(numberOfPossibilities);

    Next I would iterate through the possibilities and look for a match in (a subset of) the ‘finalObjects’ list. To be sure the matching would be done honestly during this process, I changed the value for the Ranking property after a positive match. This way, SpecificObjects that had no match yet would move up in the ranking and would be matched before SpecificObjects that already had one or more positive matches. Unfortunately, this had a very unwanted side-effect.

    Can you think of it? Let me know and put it in the comments. The answer can be found in my next post.

    By |June 6th, 2008|.Net, Linq|1 Comment