Showing posts with label Visual Studio. Show all posts
Showing posts with label Visual Studio. Show all posts

Monday, February 6, 2012

NCrunch, The Incredible TDD Tool!

I've been meaning to evaluate and review some development tools since forever. I think I waited so long just because I never found a tool that grabbed my attention to a level where it could really get me on my butt and make me jot down a review. Well, now we have such an awesomized tool - NCrunch!



Calling NCrunch just another TDD tool would be terrible injustice to it's developers.

NCrunch is -
  • An automated parallel continuous testing tool for Visual Studio.
  • A code coverage analyzer
  • A performance analyzer
  • And last, but not the least, incredibly smart!
Think about the usual steps you go through with test driven development:
  • Write test
  • Build and run tests
  • Write code
  • Build and run tests
  • Refactor code
  • Build and run tests
As a highly optimised test runner, NCrunch can knock half of these steps away by automating them completely - so you end up with:
  • Write test
  • Write code
  • Refactor code
Yes! The tests are automatically built and run in the background. Continuous feedback is provided on the fly, thereby making test development easier. As soon as the tests are build-able, NCrunch runs the tests and provides immediate feedback. Writing assertions is a pleasure!

And there's much more apart from this main feature. But, let's look at how a developer would use NCrunch. Here, we have written a simple test.


The view above shows the normal view that a developer shall have when NCrunch is disabled. Go ahead and enable NCrunch. Go to NCrunch -> Enable NCrunch. And now you see your editor shows something like this. Note that we have defined a default implementation for the Add() method that returns zero.


We shall go back and fix the method Add(). Also, you don't even need to save your files for NCrunch to be able to run your tests!


We now add another test to our suite.


While writing the test however, we see an error. This is because the test is wrong! Correct the test! I just love this level of immediate feedback! Hover over the red cross mark and it shows you a tooltip that tells you exactly what went wrong. (Click on image to view)


Fix the failing test and everything shows green again! NCrunch also handles exceptions gracefully and the tooltips indicate which exception occurred and where.

Code Coverage
The lines of code marked green indicate the parts of code that are covered by tests. This makes it very easy to spot areas that have not been covered yet, write covering code or eliminating any dead code. The following tooltip on the test tells you that the test is covered by 1 passing test.



Performance metrics
NCrunch also provides information about performance metrics and hot-spots in the tested code, thereby allowing you to identify parts of code that might induce a performance problem in the long run. The previous figure shows you the execution time of the test. The next figure shows you that the method being tested is too slow.


The yellow marker indicates that the code is executing really slow and that you should take a look to see if that's normal.

What frameworks does NCrunch support?
Supported testing frameworks are:
  • NUnit
  • MS Test
  • Xunit
  • MbUnit
  • MSpec
Supported languages and .NET versions are:
  • C#
  • VB.NET
  • F#
  • .NET Framework v2.0 and above
  • Visual Studio 2008
  • Visual Studio 2010
  • Visual Studio 11 Developer Preview
Pricing?
I'm sure that there has been a huge level of effort that has gone into developing this tool. But, the software is free to be used as long as it is in beta. Let's hope that on release the developers will price it economically.

There's a lot of other stuff that NCrunch supports that would make your life a wee bit easier. Go check out the NCrunch blog for updates! I really hope that this tool becomes a standard in everyday development for most software development firms.

Have fun with NCrunch!

Links:
NCrunch main website - http://www.ncrunch.net/
NCrunch Download - http://www.ncrunch.net/download.htm
NCrunch on Visual Studio Code Gallery - http://visualstudiogallery.msdn.microsoft.com/6946579c-c7d9-48ce-b039-994d30b85116

Monday, January 30, 2012

VSX Add-in Development Adventures: Window.Object returns NULL

I’m in the middle of developing an add-in for Visual Studio 2008, a simple one that would help our in-house code review process. If you’ve ever written a VS add-in, you’d know the basic routine – Visual Studio creates the basic class Connect derived from IDTExtensibility2, then you put in your code in the methods OnConnection, OnDisconnection, OnAddInsUpdate, OnStartUpComplete and OnBeginShutdown.

I developed a few user controls (UserControl objects) for showing some UI as tool windows. One of them was AddCommentView which is just a dumb UserControl that displays some textboxes and buttons and also takes in some input. I deployed this control as a separate DLL and linked it to the add-in. Then, as usual, the following code should do the job of creating the tool window.
if (_addCommentWindow == null)   
{    
    object objTemp = null;    
    string guid = Guid.NewGuid().ToString();    
    Window2 toolWins = (Window2) this._applicationObject.Windows;

    // Create the tool window view for adding the comment   
    _addCommentWindow = toolWins.CreateToolWindow2(_addinInstance, "Controls.dll", 
        "Controls.AddCommentView", "Add Comment", "{" + guid + "}", ref objTemp);
}    

And like always it worked just fine till I tried to test it and that’s when I realized something wasn’t quite right.
The CreateToolWindow2 method has two outputs – the tool window (which is returned by the method) and the hosted user control (the ref parameter ‘objTemp’ in this case). The hosted user control can also be retrieved through the Window.Object property of the returned tool window. The problem was – no matter what I tried the Window.Object property always returned null and so did ‘objTemp’.
AddCommentView addCommentViewControl = _addCommentWindow.Object as AddCommentView;   
addCommentViewControl.StartLine = selection.AnchorPoint.Line;    
addCommentViewControl.EndLine = selection.ActivePoint.Line;

The solution – I was acting dumb, very dumb. Visual Studio requires all hosted controls to be visible to COM. After adding the attribute to the entire assembly using [assembly: ComVisible(true)] , everything started working like a charm (you can apply it even to the individual control if you don’t want to make the entire assembly COMVisible).

Defining custom Dictionary keys in C#

Ever so often we come across cases where we need to store objects mapped to other objects in a Dictionary. And in most of these cases, the default solution of using the object reference as a key doesn’t really work. For example, if an object Person { Name = “Foo” } is mapped to value ‘x’, another object Person { Name = “Foo” } does not get us to the value ‘x’, although we probably would expect it to return ‘x’.
class Person    
{     
    public int Age { get; set; }     
    public string Name { get; set; }     
}

class Program    
{     
    static void Main(string[] args)     
    {     
        var p1 = new Person() { Age = 30, Name = "p1" };     
        var p2 = new Person() { Age = 31, Name = "p2" };     
        var p3 = new Person() { Age = 32, Name = "p3" };
        var personVsBonus = new Dictionary<Person, int>();    
        personVsBonus[p1] = 1000;     
        personVsBonus[p2] = 2000;     
        personVsBonus[p3] = 3000;
        var personToFind = new Person() { Age = 31, Name = "p2" };    
        Console.WriteLine(personToFind.Name + " will be given a bonus of " + personVsBonus[personToFind]);     
    }     
}     

The above program gives throws a KeyNotFoundException as the dictionary was not able to locate the entry searched as it was doing a reference comparison.
In such cases you need to define your own implementation of what the dictionary should consider as the key value. In the example we just discussed, we might like the property Person.Name to be considered as the key. Whenever a dictionary needs to decide where an item should be located, it calls GetHashCode(), whose return value decides where the item shall be stored. If GetHashCode() returns the same value for two different objects, the Equals() method is called with both objects being compared. The result of the Equals() method tells the dictionary whether the objects are the same or different.


Solution 1:
Implement the IEquatable interface for the Person class. This means that, “Hey, now the Person object will tell you whether it is the same as another Person object!”. You also need to override the Object.GetHashCode() method and write a good hash generating algorithm that generates unique values (int). Here, I use a simple method that just returns the length of the person’s name.
    class Person : IEquatable<Person>
    {
        public int Age { get; set; }
        public string Name { get; set; }
 
        #region IEquatable<Person> Members
 
        public bool Equals(Person other)
        {
            return this.Age.Equals(other.Age) 
                && this.Name.Equals(other.Name);
        }
 
        #endregion
 
        public override int GetHashCode()
        {
            return this.Name.Length;
        }
    }

Run the program after making these additions and the program works fine. The dictionary is now able to find appropriate values.

Solution 2:
There will be times when the key type might be a sealed type or you might not be allowed to change the key object’s properties. The Dictionary type provides us the IEqualityComparer interface that we can implement to provide our custom definitions based on the key object’s properties without having to modify the key’s properties.

Here is the modified code:

    class Person
    {
        public int Age { get; set; }
        public string Name { get; set; }
    }
 
    class PersonEqualityComparer : IEqualityComparer<Person>
    {
        #region IEqualityComparer<Person> Members
 
        public bool Equals(Person x, Person y)
        {
            return x.Age.Equals(y.Age)
                && x.Name.Equals(y.Name);
        }
 
        public int GetHashCode(Person obj)
        {
            return obj.Name.Length;
        }
 
        #endregion
    }

Also remember to use the comparer object while creating the dictionary.

var personVsBonus = new Dictionary<Person, int>(new PersonEqualityComparer());

Run the program after making these changes and the program works just fine!

The most important thing to remember here is that your definition of GetHashCode() shall decide how fast your dictionary can lookup an entry. Be very careful while taking these solutions into consideration as weak hash generation might lead you to long-term scalability issues where the dictionary might take more and more time to lookup entries in large dictionaries.

Sunday, January 29, 2012

TaskList in Visual Studio - Making it better

It was great to come across a new feature in Visual Studio - The TaskList. Well, yes it isn't new but, it certainly was new to me. I had never really come across this wonderful feature until last week when secretGeek blogged that code would suck less if the compiler could raise an error when a // TODO token was detected. A comment from Goran indicated that it was completely possible with the current versions of Visual Studio.
A //TODO: token.
Are shown in VS if you click TaskList. Couldn’t live without this one :)
Yeah, sure. Can’t live without it. Although the compiler doesn’t throw you an error, it indicates all parts of code where such tokens appear and hence can be taken care of easily.

How To Use
You can use the TaskList comments for:
  • Features to be added
  • Problems to be corrected
  • Classes to implement
  • Place-markers for error handling code
  • Reminders to check in the file
Add your comment in the code preceded by the token.    

Once done, open up the TaskList from the View menu.

Once the TaskList is up you will see something like this.

The TaskList also allows custom tokens to be included. Go to Tools –> Options –> Environment –> TaskList.

User Tasks
You can add your own tasks in the TaskList by selecting the ‘User Tasks’ selection from the dropdown list on the TaskList toolbox. These tasks aren’t associated with code, but will allow users to add their own high level tasks.

Extending the TaskList
I would like to see the following additional options in the TaskList:
  • Task Alarms – which would associate an alarm with a high priority comment to help just in case you forget to take care.
  • User Tasks to be more specific (by having a file anchor like ‘Comments’) to allow user tasks to be associated with a particular line in code.
And no, I’m not waiting on Microsoft to extend it in some other version of Visual Studio. I’m starting right away to write a package that would do this for me, hopefully.

More Things to Remember
With Visual Basic projects, the Task List displays all of the comments in the project. With Visual C# and Visual J# projects, the Task List displays only the comments that are found in the files currently opened for edit. With Visual C++ projects, the Task List displays only the comments that are found in the file currently active in the editor.

C# 3.0 for Beginners - Query Execution in LINQ

The execution of queries written is different from what a new LINQ user would perceive it to be. The query isn’t evaluated and the result is not stored in the query variable until the foreach iteration (where the values are actually required) or a manual iteration using the underlying GetEnumerator and MoveNext methods. The query variable only stores the query commands. This is concept is referred to as deferred execution.
public static void GetIExplorer()
{
    //  1. Data Source
    Process[] processes = Process.GetProcesses();

    //  2. Query Creation
    IEnumerable<int> query =
       from p in processes
       where p.ProcessName.ToLower().Equals("iexplore")
       select p.Id;

    //  3. Query execution
    //  This is the part where the query is evaluated
    //  and result is stored in the query variable.
    foreach (int pid in query)
    {
        Console.WriteLine("Process Id : "+pid);
    }
}

As the query variable doesn’t store the results, you can execute it as many times as you like. If a data source is updated at regular intervals, you could retrieve the latest results every time you iterate over the query variable.


The figure shown above shows information about the query variable ‘query’. The Results View section shows the results of query execution and it also informs the user that “Expanding the Results View will enumerate the IEnumerable” i.e. perform the query execution for debugging.

Forcing immediate execution of queries
Immediate execution of queries is forced for queries that perform aggregation functions over the data retrieved from query evaluation. These functions include Count, Max, Min, Average etc. These queries execute without an explicit foreach statement because the query itself would use a foreach statement to calculate the result.

The following query returns the number of processes identified as “IExplore.exe”.
//  Calculate the number of "iexplore" processes
int numberOfProcesses = query.Count();

Execution results can be cached (if need be) for temporary processing using the ToList() and ToArray() methods as shown below:
//  Caching results using ToList() and ToArray() methods.
List<int> queryResult =
(from p in processes
    where p.ProcessName.ToLower().Equals("iexplore")
    select p.Id).ToList();

Array inferredQueryResult =
    (from p in processes
    where p.ProcessName.ToLower().Equals("iexplore")
    select p.Id).ToArray();


C# 3.0 for Beginners - Learning LINQ - An Overview

I’m probably quite late to provide an overview on LINQ, which is by now a lot more popular than the time when I actually had started hearing about it.

Well, this is expected to be a series of posts that would help other rookies like me who haven’t yet started learning LINQ yet. So, lets get started. To begin with I’m providing here an overview of LINQ (Language Integrated Query).

LINQ was introduced by Microsoft with the objective to reduce the complexity of accessing and integrating information. With the LINQ project, Microsoft has added query facilities to the .Net Framework that apply to all sources of information, not just relational or XML data. Everyday programmers write code that accesses a data source using looping and/or conditional constructs etc. The same constructs can be written using query expressions that are far lesser in code size. LINQ makes it possible to write easily readable and elegant code. The examples that follow will imply how easily understandable LINQ code can be.

LINQ defines a set of standard query operators that you can use for traversal, filter and projection operations. These standard operators can be applied to any IEnumerable<T> based information source. The set of standard query operators can be augmented with new domain-specific operators that are more suitable for the target domain or technology. This extensibility in the query architecture is used in the LINQ project itself to provide implementations that work over both XML (LINQ to XML) and SQL (LINQ to SQL) data. Lets write some code to understand the query operators in more detail:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Diagnostics;

/// <summary>
/// Using standard query operators.
/// </summary>
public static void GetIExplorer()
{
    //  1. Data Source
    Process[] processes = Process.GetProcesses();

    //  2. Query Creation
    IEnumerable<int> query = from p in processes
                             where p.ProcessName.ToLower().Equals("iexplore")
                             select p.Id;

    //  3. Query execution
    foreach (int pid in query)
    {
        Console.WriteLine("Process Id : "+pid);
    }
}

All LINQ query operations consist of three distinct operations:

Identify the data source
Query creation
Query execution

Calling the method would show you the currently running Internet Explorer processes (their process ids). The heart of the method lies in the following statement of our program.
IEnumerable<int> query = from p in processes
                         where p.ProcessName.ToLower().Equals("iexplore")
                         select p.Id;

The expression on the right hand side of this statement is called the query expression. The output of this expression is held in the local variable ‘query’. The query expression operates on one or more information sources by applying the query operators from the standard or domian specific set of query operators. We have used standard query operators here namely where and select.

The from clause select the list of processes which becomes the input for the where operator which filters the list and selects only those elements that satisfy the condition specified with the where operator. The selected elements are then processed by the select operator that determines any specific information selection for each element.

The above statement can also be written using explicit syntax as shown below:
IEnumerable<int> query = Process.GetProcesses()
               .Where(s => s.ProcessName.ToLower().Equals("iexplore"))
               .Select(s => s.Id);

This form of query is called a method-based query and the arguments to the query operators are called lambda expressions. They allow query operators to be defined individually as methods and are connected using the dot notation. I will deal with lambda expressions in my following posts.

Anonymous methods in C#


An anonymous method is just a method that has no name. Anonymous methods are most frequently used to pass a code block as a delegate parameter.

Before C# 2.0, the only way to declare a delegate was to use named methods as shown in the example below

// Create the delegate
public delegate void Display(string message);

// Create the method
public static void DisplayOnConsole(string myMessage)
{
    Console.WriteLine(myMessage);
}

public static void Main(string[] args)
{
    // Here, the delegate is instantiated with the
    // method which should be invoked.
    Display myDisplay = new Display(DisplayOnConsole);

    // Invoke
    myDisplay("Hello World!");
}

Then C# 2.0 introduced the concept of anonymous methods.

// Creation of delegate with an anonymous method
Display newDisplay = delegate(string msg)
{
    // Anonymous method body
    Console.WriteLine(msg);
};

// Invoke
newDisplay("Hello World using Anonymous methods.");

The difference here is quite apparent. Creation of a new method to act as a handler is not required; the delegate itself specifies what should be done when invoked. Anonymous methods reduce the coding overhead in instantiating delegates because you do not have to create a separate method. Specifying a code bolck instead of a delegate can be useful in situations where creation another method might seem an unnecessary overhead.

Some other points to remember:
  • There cannot be any jump statements like goto, break or continue inside the code block if the target is outside the block and vice versa.
  • The scope of parameters of an anonymous method is the anonymous code block.
  • No unsafe code can be used within the anonymous code block.
  • The local variables and parameters whose scope contains an anonymous method declaration are called outer variables of the anonymous method. 

In the following code the variable x is an outer variable.

int x = 0;
Display newDisplay = delegate(string msg)
{
    Console.WriteLine(msg + x);
};
  • An anonymous method cannot access the ref or out variables of an outer scope.
C# 3.0 introduces lambda expressions which are pretty much similar to anonymous methods but more expressive and concise. Applications written using .NET Framework version 3.5 and higher should make use of lambda expressions instead of anonymous methods. I will discuss lambda expressions in detail after I start with LINQ (Language Integrated Query) in my following posts.

Did you know the two uses of ‘default’?

Well, maybe you do and maybe you don’t. And I’m not trying to start a series of posts tagged “Did you know?”, I guess Sara Ford is much better at it.

You’ve used the default keyword in C# as many times as possible in switch statements to indicate the default operation to be carried out. That’s one place where you would normally use the default keyword.

You can also use the default keyword in generic code where it specifies the default value of the type parameter which is null for reference types and zero for value types. In generic programming it is always difficult to guess what default value to assign to a parameterized type T when you don’t know information such as whether T is a value/reference type; if it’s a value type, is it an elementary type or a struct? This is where the default keyword is used to find out the exact default value for the current type. Here is how it would be used:

class MyGenerics<T>
{
    public void MyMethod()
    {
        T myVar = default(T);
     
        //...
        //...
        int defaultValue = default(int);
    }
}

The default value for reference types is null, for value types is zero and for struct types each member is initialized with it’s default value depending on whether it is a value or reference type.

Monday, July 19, 2010

A compact PC-Lint error output file parser

This code has been hanging around in my drafts folder for quite some time now. I needed to get it out. I wrote this simple parser for extracting information from the .out file PC-Lint provides as output after its analysis. This information will further be fed to a VS add-in that would integrate this content with the editor. It's going to be a cool one! I'm going to setup the alpha version of the add-in next month on Google Code.

Here's the code.

public class PCLintOutputReader
{
    public PCLintOutputReader(string filePath)
    {
        _content = File.ReadAllText(filePath);
    }

    public List<ErrorMessageInfo> ParseTextErrorMessages()
    {
        const string errorPatternAsString = @"T:\s*(?<Type>\w*)\r\n"
                                          + @"N:\s*(?<ErrorNumber>[0-9]*)\r\n"
                                          + @"F:\s*(?<FileName>.*)\r\n"
                                          + @"L:\s*(?<LineNumber>[0-9]*)\r\n"
                                          + @"M:\s*(?<Message>.*)\r\n";

        Regex errorPattern = new Regex(errorPatternAsString, RegexOptions.Compiled | RegexOptions.IgnoreCase);

        var errorMessages = new List<ErrorMessageInfo>();
        var matches = errorPattern.Matches(_content);
        foreach (Match match in matches)
        {
            GroupCollection groups = match.Groups;
            errorMessages.Add(
                ErrorMessageInfo.Parse(groups["Type"].Value, groups["ErrorNumber"].Value, groups["FileName"].Value,
                    groups["LineNumber"].Value, groups["Message"].Value)
            );
        }

        return errorMessages;
    }

    private string _content;
}


public class ErrorMessageInfo
{
    public ErrorMessageInfo() { }
    public MessageType Type { get; set; }
    public int ErrorNumber { get; set; }
    public string FileName { get; set; }
    public int LineNumber { get; set; }
    public string Message { get; set; }

    public static ErrorMessageInfo Parse(string aType, string aErrorNumber, string aFileName, string aLineNumber, string aMessage)
    {
        ErrorMessageInfo errorMessage = new ErrorMessageInfo();
        switch (aType)
        {
            case "Info":
                errorMessage.Type = MessageType.Info;
                break;
            case "Warning":
                errorMessage.Type = MessageType.Warning;
                break;
            case "Error":
                errorMessage.Type = MessageType.Error;
                break;
            default:
                throw new ArgumentException("Could not identify the type of PC-Lint error.", aType);
        }

        int temp = 0;
        int.TryParse(aErrorNumber, out temp);
        errorMessage.ErrorNumber = temp;

        int.TryParse(aLineNumber, out temp);
        errorMessage.LineNumber = temp;

        errorMessage.FileName = aFileName;
        errorMessage.Message = aMessage;
        return errorMessage;
    }
}


public enum MessageType
{
    Info,
    Warning,
    Error
}

Disclaimer: This is a very amateur implementation of the solution. Kindly use the code at your own risk and don't blame me if your laptop bursts into flames. Please forgive any obvious coding convention errors. And let me know if you find any bugs.
Have fun!