Steve Michelotti

C#, ASP.NET, and other stuff

  Home  |   Contact  |   Syndication    |   Login
  56 Posts | 1 Stories | 176 Comments | 52 Trackbacks

News






Google My Blog

Tag Cloud


Archives

Post Categories

Image Galleries

Articles

Blogs

Tuesday, December 02, 2008 #

In the past couple of years, I had the unique opportunity to lead of team of developers building one of the highest (if not THE highest) volume .NET application in the world.  With more than 3 billion requests per day and an SLA of 99.99% of requests under 250ms, we had some exciting challenges. Because the application was so performance intensive, we heavily utilized a huge in-memory cache.  Because of the size of our cache, we had some interesting challenges to overcome with .NET garbage collection in order to satisfy our SLA.  This led us to working with Microsoft to implement GC Notifications which were released in .NET 3.5 SP1.

Of course the details of this could be a white paper unto itself but here is a 20 minute interview on ARCast.TV explaining some of the details.

64-bit Computing Technology for Highly Scalable Applications


Sunday, November 23, 2008 #

I often get asked by other developers at work or during presentations about various tools that I use.  Most of the tools I use are relatively well known, but I'm going to create this post so that I have a single point where you can download everything without a bunch of Googling.  Almost all of the tools on this list are free.  My only disclaimer is that this is simply my personal list of the tools I use most often.  If you're looking for a *real* list that is extremely comprehensive, then I recommended checking out Scott Hanselman's Tools List.

There are many tools listed below but, generally, the tools I cannot live without and use on a daily basis are: Reflector, SlickRun (or Executor), PowerShell, TextPad, FxCop, Royal TS, Web Dev Helper, Firefox Live HTTP Headers, ZoomIt, and Process Monitor.

Misc Dev Tools

  • PowerShell - There is definitely a learning curve with PowerShell but once you get comfortable with it, you have the power of the .NET framework from the command line.
  • TextPad - I've been using this text editor for years and I generally believe that you should stick with the text editor that you are most familiar and skillful with.  I love the syntax highlighting for all kinds of document classes.
  • Log Parser - Essential tool that allows you to query a variety of file formats (e.g., IIS, ETW, CSV, XML, etc.).
  • Visual Log Parser  - Provides a great GUI over top of Log Parser.  Very easy to work with compared to command line - particularly with the ability to save queries to files.
  • Rock Scroll - This is a cool VS.NET add-in that I originally saw during a Scott Hanselman presentation.  It gives you a nice scroll bar that "shows" the code as well as some context highlight of tokens.
  • VS.NET 2008 Power Commands - This adds a host of commands to VS.NET which the IDE should have had on its own.
  • GhostDoc - This VS.NET add-in allows the quick creation of method comment stubs.
  • Database Publishing Wizard - Let's you quickly script your entire database including optionally scripting the data.
  • Snippy - I use this tool exclusively to create Visual Studio code snippets for general every day development as well as presentations.
  • NUnit - NUnit, MSTest, xUnit, MBUnit - Use what makes you happy.
  • Moq - This is currently my favorite mocking framework.  RhinoMocks and TypeMock are also good but I believe Moq is more intuitive with a smaller learning curve.
  • Tortoise - If you use Subversion, this is obviously a must.  But even if you don't use, there are features such as the Diff tool that are great (and free).
  • WinDbg - A big learning curve if you have never used it. But if you are working on an application where detailed analysis of memory is required, then it's literally impossible to debug some of those issues without this tool.
  • LinqPad - If you're working with LINQ to SQL, this is your "Query Analyzer".  Very robust tool that allows you to write LINQ queries over any IEnumerable including data base connections.
  • XML Notepad 2007 - This is a great, lightweight, free editor for XML files.  The 2007 version is vastly improved over its original.

Code Analysis

  • Reflector - There are certain days it would be impossible to do your job without this tool.  Also check out the Reflectors Add-Ins on CodePlex.
  • FxCop - Stand-alone GUI and command line for build server are essential.
  • NCover - The new version costs money now but it's more than worth it.
  • StyleCop - This relatively new public tool has been used internally by Microsoft for years.  I believe it's going to be used more and more in the coming years. Unlike FxCop which looks at your binary code, StyleCop looks at your source for conformance with style coding standards.
  • SourceMonitor - Being able to quickly identify where your code complexity lives is essential to refactoring to cleaner designs.  This tool does a great job of that.

Web Development

  • Web Dev Helper - This IE add-in is essential to web development.  If you're doing AJAX development, this is a must have.
  • Firefox Live HTTP Headers - If you work with HTTP status codes, need to understand when redirects are happening, etc. this tool is essential to give you the entire picture of HTTP headers.
  • IE Developer Toolbar - Another invaluable IE add-in to be able to quickly select and manipulate DOM elements.
  • Fiddler - HTTP debugger which shows all details about the HTTP request/response.
  • IIS 6.0 Resource Kit - Comes with many useful tools including Log Parser.  My favorite is TinyGet.

Utilities

  • SlickRun - This is a launcher I cannot do without and I use it all day long.  I barely have to pick up the mouse to click the Start button because of how robust this launcher is.  It is a must have.
  • Executor - Wow, based on a comment by Libor, I have added Executor to my list and I am now a believer.  This definitely gives SlickRun a run for it's money!
  • ZoomIt - If you do presentations of any kind (to clients, developers, etc.) this is absolutely a must have.  Very easy to use and the features are robust.
  • Royal TS  - If you work with Remote Desktop at all, then this is a must have. This free tool allows you to easily organize your remote desktop sessions as well as bounce back and forth between different active sessions with ease.
  • Process Monitor - This is a must have for debugging "mysterious" issues.  They've rolled RegMon, ProcessMon, and FileMon into one now.
  • Password Safe - This is a lightweight, portable, and easy to use password storage app.
  • Clean Sources - Windows shell app that gives the ability to quickly remove the bin and obj directories from your visual studio solutions.
  • Consolas Font - I set Visual Studio and all my text editors to use this font.
  • Live Writer - I use Live Writer for all my blog posts and it's generally considered the best tool out there.  There are some other features I'd like to have in it but it does the job well.

Enjoy!


Saturday, November 22, 2008 #

In a previous post, I discussed how to identify the technologies you want to learn and come up with a personal learning road map, so to speak.  But when it comes time to dive into one specific technology, how do you go about learning something new?  In fact, I almost always ask that question during developer interviews.  The most disappointing answer I get to that question is, "well, I will Google it and read articles about it." That doesn't really show a very deep level of enthusiasm or commitment.

Obviously, different people have different learning styles.  Some people do well learning from a book whereas that is useless for other people.  Some people do well in instructor led training whereas that is useless for other people.  In my opinion, it is very important to understand how *you* personally learn best but don't let that limit you.  In other words, make your learning as well-rounded as possible.  For example, if you feel you learn best from hands-on practice, that's great but don't let that be an excuse to not buy a book. Ultimately, you're never going to be able to learn every aspect with solely hands-on practice because there may be features you were not even aware of had you not read about it in a more complete reference like a book.

When MVC came out last year, I decided that I wanted to learn it as it was quite interesting to me.  This is how I learned it and this is the approach that I typically use for any technology.  Regardless of the technology that you want to learn, this type of approach can be used.

Much of this might seem intuitive and freely available on most Microsoft sites.  But the keys are: 1) be systematic and organized in your approach, and 2) keep track of everything you're about to do and what you've done in written or electronic form.  You need the systematic documentation to keep you goal oriented, focused, and on-track.

Step 1 - Identify specific quality sites and read EVERYTHING on these sites. For MVC, there was MVC on ASP.NET. There are a ton of links to articles, training, and additional resources that you'll find on sites like these. Read everything on these sites.

Step 2 - Identify and subscribe to quality blogs. For MVC, there was Scott Gu, Scott Hanselman, Stephen Walther, etc. There will be other blogs like these for whatever technology you are currently learning - find them.  It's great to read articles (from step 1) but blogs can be extremely valuable with information from people that are already experts in the technology or are using the technology hands-on.  Use them.

Step 3 - Web casts.  For MVC, there is a page dedicated to MVC web casts.  You can read all the articles in the world but web casts can give you a great high level picture while seeing live demonstrations that can get you up to speed quicker than floundering yourself. If Microsoft gives you a page with 10 web casts, watch all 10.  In fact, should write down specific days and which web casts you are going to watch on which days and treat watching them like goals. Get it done.

Step 4 - Get a book. Articles and web casts are great but a book is a more complete reference that will go into details of your technology in greater depth than you'd get from an article or blog post. Use the consumer feedback on sites like Amazon.com to determine the best books to get if you're unsure.

Step 5 - Hands-on Labs.  You can read/watch all the articles/books/webcasts in the world but there is simply no substitute for hands-on experience.  Microsoft does a decent job providing guided hands-on labs in many new technologies.  These typically (but not always) do a good job providing systematic hands-on experience in the primary areas.

Step 6 - Hands-on Project.  Hands-on labs are great but, ultimately, they are totally guided.  All the code is given to you.  To really become good at something you *need* to flounder a little.  You need to run into problems and figure them out.  Give yourself a little side project outside of work to build some sort of application that does XYZ.  Although this is step 6, this is the most important step.  There is simply no substitute for hands-on experience. But you want that hands-on experience to be based on an already strong foundation from other learning materials.

Step 7 - Write an article. This might be something as simple as a blog post. Or you may decide to go as far as to write an article for MSDN Magazine or Visual Studio Magazine.  Having to write something down helps organize your thoughts especially if you know other people are going to read it. I've certainly had times when people politely (or not so politely) told me that something I wrote on my blog made me look like an idiot so you want to give it at least a little thought first.

Step 8 - Give a Presentation. This one often scares people off but it shouldn't. Set a goal for yourself to give a presentation on your topic in a 6 month timeframe.  You'll have plenty of time to learn it. This presentation might be for 5 developers at your company, maybe your entire development staff, maybe a local users group, maybe a regional Code Camp, maybe Tech Ed!  Either way, this is a huge motivating step.  You know that if you're going to get up in front of a room full of your fellow professional developers then you better know what you're talking about!

If you're learning a new technology that you're truly interested in, then it should be an enjoyable thing to totally immerse yourself.  With the amount of freely available training materials these days, you have only yourself to blame if you don't take full advantage.  Either way, next time you're asked in an interview how you learn something new, please don't tell them you Google and leave it at that.


How do you stay up on new technologies?  How do you approach learning a specific new technology?  The first thing you have to accept is that the Microsoft technology stack has gotten so vast that it is simply impossible for a single person to be an expert in everything.  This is the most important aspect to remember. This post is simply to describe my personal approach for staying up on new technologies in the hopes that other people will find something valuable in this to add to their toolbox.  In terms of a high level philosophy, my outlook is that I want to be able to speak intelligently about as many technologies as possible, but then be able to consider myself an "expert" in a few of the most important.  It is simply not possible to be an expert in everything.

Step 1 - Make a list.  Literally create a spreadsheet for yourself for all the technologies that you already know or want to learn about. Consider this your own person "Skills Matrix."  You want to be able to see, on one page, everything you know or don't know.  I've been keeping my own list for 4 years and it's a working document that I'm constantly updating. My personal list looks something like this:

  • C# language / .NET Framework
  • C# 2.0 (generics, anonymous methods, etc.)
  • C# 3.0 (lambdas, object initializers, etc.)
  • ASP.NET 2.0 (Membership, MasterPages, etc.)
  • ASP.NET 3.5 (New web server controls, etc.)
  • Windows Apps
  • XSLT
  • OO Design / Architecture
  • Design Patterns
  • Web Services (asmx)
  • LINQ to SQL
  • IIS 6.0
  • IIS 7.0
  • WSE
  • Windows Workflow Foundation
  • Windows Communication Foundation
  • Windows Presentation Foundation
  • CardSpace
  • Commerce Server
  • Oracle
  • Microsoft AJAX
  • jQuery
  • InfoPath 2003/2007
  • BizTalk 2004
  • BizTalk 2006
  • Enterprise Library Validation (VAB)
  • ASP.NET MVC
  • MSBuild
  • SQL Server
  • SQL Reporting Services
  • SQL Integration Services
  • SQL Analysis Services
  • SQL Notification Services
  • SQL Service Broker
  • MOSS
  • Silverlight
  • Entity Framework
  • ADO.NET Data Services
  • ASP.NET Dynamic Data
  • Enterprise Library Logging, Data block, Exception Handling, etc.
  • Microsoft Expression

Step 2 - Categorize your list.  If you're not overwhelmed with the list you created above then you're doing something wrong. Remember, the goal is to not be an expert in everything.  The next step is probably the most challenging - you must put each item on the list in 1 of 4 categories: 

  • Expert - I'm a true Expert in this technology and I could talk with anyone in true technical depth about any aspect of it. I can complete any hands on task given to me with mastery.
  • Solid - I'm Solid in this technology with some great professional hands-on experience but not a *true* expert.
  • Low - I have *some* experience so I can speak intelligently about this technology but my expertise is "low".
  • None - I may or may not have read about this technology but I definitely don't have any hands on experience and I don't really know what I'm talking about.

In order to be successful with this step and, ultimately, successful learning new technologies you have to be very honest with yourself with Step #2.  Remember, you're not sharing this list with anyone so if you have only 1 item in Expert and 30 items in None, that's OK - no one will know but you.  If you've got 40 items on your list and you've got 20 in the Expert category, then you're *definitely* doing something wrong and are not being honest with yourself.  Trust me, you're not a true expert in 20 technological areas.

Step 3 - Identify Key Areas.  Now it's time to start narrowing down what you're actually going to dive deeper into.  There are three main categories I have for this:

  1. Technologies on the list that you're very interested in but you don't have a lot of opportunity to use them in your professional life. 
  2. Technologies on the list that your employer is going to consider very important but the technology is not incredibly engaging to you. 
  3. Technologies on the list that both interest you greatly (#1 above), and your employer deems valuable (#2 above).

The technologies in #3 are the best ones to start with.  But don't forget about #1 and #2 as those are important as well.  If you list has 40 items on it, focus on about 5 for this step #3 here.

Step 4 - Determine where you want to go.  Now that you've identified about 5 areas in step 3, you need to look at what category you're in now and then figure out where you want to go.  If you're a "None" in all 5 areas and you want to go to "Expert" in all 5, then you're doing something wrong.  In fact, I think, from a goal perspective, it would be a mistake to go above 1 item for the Expert category.  There might be one or two where you want to go from None to Low because you want to be able to speak intelligently about it but don't have a need to be a true hands on expert - once you attain that level, it's time to move on to the next thing.  There might be an area where you're already very solid with a couple of years of experience but you want to go to the next level and become an Expert.  Bottom line, it varies for each item.

Step 5 - Repeat steps 1-4.  Going from None to Low is not difficult for most items.  You're going to read articles, do some hands on labs, etc. and you'll feel comfortable talking about it.  But you want to constantly re-asses.  When I started my own personal list 4 years ago, it probably only had 20 items on it but it's obviously going to grow as new technologies emerge.  Make sure to add new items to your None category as they come out and keep re-assessing Step 3 to constantly identify the areas where you want to learn.

Much of this might seem pretty intuitive but I think the real key is to keep track of everything in written (or preferably) electronic form. 

There are some technologies where you're going to want to go to the next level and truly improve your current knowledge level. I discuss my own process here in my Approach For Learning a Specific New Technology.


Monday, October 27, 2008 #

The code samples from my recent presentation at the Maryland CMAP code camp can be downloaded here:

N-Tiered LINQ to SQL

MVC and Unit Testing

Wednesday, October 08, 2008 #

The code samples from my recent presentation at the CMAP Main meeting can be downloaded here: MVC and Unit Testing. The direct download link is here.


Sunday, October 05, 2008 #

When .NET 2.0 was released, a TryParse() method was added to many value types such as Int32, DataTime, etc. This was a huge improvement because there was no longer a need to catch expensive exceptions and drag down performance. However, one drawback of the TryParse() method is that the syntax is a little clunky. The most common example looks like this:

   1:  Person person = new Person();
   2:  string value = "21";
   3:  int num;
   4:  int.TryParse(value, out num);
   5:  person.Age = num;

So it's great that we can do all this without having to catch exceptions but it definitely seems more complex than it has to be given that all we're trying to do is assign an integer to the Age property and we need this many lines of code.  We can use Extension methods to make the consuming code much more friendly - a single line of code:

   1:  person.Age = value.TryParseInt32();

To implement the static class for the extension methods, we *could* implement each TryParseXX() method like this:

   1:  public static int TryParseInt32(this string value)
   2:  {
   3:      int result;
   4:      int.TryParse(value, out result);
   5:      return result;
   6:  }

However, now we've got the ugly, repetitive code in numerous methods inside that class. On the good side, at least we've encapsulated the repetitive code inside a single class, but we can leverage a generic delegate and generic method to even avoid the repetition inside that class.

   1:  private delegate bool ParseDelegate<T>(string s, out T result);
   2:   
   3:  private static T TryParse<T>(this string value, ParseDelegate<T> parse) where T : struct
   4:  {
   5:      T result;
   6:      parse(value, out result);
   7:      return result;
   8:  }

This allows our TryParseInt32() implementation to now be a single line of code:

   1:  public static int TryParseInt32(this string value)
   2:  {
   3:      return TryParse<int>(value, int.TryParse);
   4:  }

The ParseDelegate<T> is generic that matches the signature of all the TryParse() methods. So we can imply pass in the int.TryParse delegate and it will be executed *inside* the re-useable TryParse<T> method that I have created.  This utility class can be used in all kinds of different string parsing situations.  Here is the complete code for the TryParseExtensions class:

   1:  public static class TryParseExtensions
   2:  {
   3:     
   4:      public static int TryParseInt32(this string value)
   5:      {
   6:          return TryParse<int>(value, int.TryParse);
   7:      }
   8:   
   9:      public static Int16 TryParseInt16(this string value)
  10:      {
  11:          return TryParse<Int16>(value, Int16.TryParse);
  12:      }
  13:   
  14:      public static Int64 TryParseInt64(this string value)
  15:      {
  16:          return TryParse<Int64>(value, Int64.TryParse);
  17:      }
  18:   
  19:      public static byte TryParseByte(this string value)
  20:      {
  21:          return TryParse<byte>(value, byte.TryParse);
  22:      }
  23:   
  24:      public static bool TryParseBoolean(this string value)
  25:      {
  26:          return TryParse<bool>(value, bool.TryParse);
  27:      }
  28:   
  29:      public static Single TryParseSingle(this string value)
  30:      {
  31:          return TryParse<Single>(value, Single.TryParse);
  32:      }
  33:   
  34:      public static Double TryParseDoube(this string value)
  35:      {
  36:          return TryParse<Double>(value, Double.TryParse);
  37:      }
  38:   
  39:      public static Decimal TryParseDecimal(this string value)
  40:      {
  41:          return TryParse<Decimal>(value, Decimal.TryParse);
  42:      }
  43:   
  44:      public static DateTime TryParseDateTime(this string value)
  45:      {
  46:          return TryParse<DateTime>(value, DateTime.TryParse);
  47:      }
  48:   
  49:      #region Private Members
  50:   
  51:      private delegate bool ParseDelegate<T>(string s, out T result);
  52:   
  53:      private static T TryParse<T>(this string value, ParseDelegate<T> parse) where T : struct
  54:      {
  55:          T result;
  56:          parse(value, out result);
  57:          return result;
  58:      }
  59:   
  60:      #endregion
  61:   
  62:  }

Saturday, October 04, 2008 #

Several weeks ago (before the release of the CTP5 of MVC) I posted a way to leverage the EntLib Validation Application Block with MVC. Since then CTP5 has been released and this finally includes a mechanism for reporting validations.  It is important to note that it does not include the mechanism for *how* to do validation but rather how to *report* validations.  This is actually a great thing because, first off, it allows the flexibility to utilize whatever validation framework you please rather than forcing you into a specific framework.  Additionally, it encourages validations to be handled in the business/domain layer rather than the presentation layer.  Stephen Walther shows an example here for how to leverage the EntLib VAB with the latest version of MVC. In this post, I'm going to expand on that including discussing specific issues that need to be addressed in more real-world applications.

Let's take an example:

 

In the simple case, let's say we pass a Contact object as the Model on to the View. To display and validation the first name we can simple do this:

   1:  <%=Html.TextBox("FirstName")%>
   2:  <%=Html.ValidationMessage("FirstName") %>

Then in our server side C# code during postback we can do this:

   1:  foreach (var validationResult in validationResults)
   2:  {
   3:      this.ViewData.ModelState.AddModelError(validationResult.Key, null, validationResult.Message);
   4:  }

This is all well and good because the validationResult.Key is going to be "FirstName" (e.g., if the first name was not valid).  Basically it is just the property name.

This worked fine because the property name matched the string we gave the the Html.TextBox() and Html.ValidationMessage() methods. We don't have to look far to see that this will not always be this simple.  Let see what it looks like to show our Contact's Street Address:

   1:  <%=Html.TextBox("Address.StreetAddress")%>
   2:  <%=Html.ValidationMessage("Address.StreetAddress")%>

Notice that now we have to specify "Address.StreetAddress" because Address is a property on the Contact object. If the street address is not valid, the C# code above will not work because the validationResult.Key is going to be "StreetAddress" but the key we need for the MVC ViewPage is "Address.StreetAddress". So basically we need is a helper method that is going to translate the Key from the ValidationResult into the key needed for the ViewPage. That is, we want to translate "StreetAddress" into "Address.StreetAddress" in this case. Even more specifically, we have to set the "prefix" correctly because we know the property names are going to match.

There are several ways to solve this. One way is to use a simple property prefix map like this:

   1:  static Dictionary<Type, string> propertyPrefixMap = new Dictionary<Type, string>()
   2:  {
   3:      { typeof(Address), "Address" },
   4:      // Add other types here
   5:  };
   6:   
   7:  public static string ToMvcKey(this ValidationResult validationResult)
   8:  {
   9:      string prefix;
  10:      propertyPrefixMap.TryGetValue(validationResult.Target.GetType(), out prefix);
  11:   
  12:      if (string.IsNullOrEmpty(prefix))
  13:      {
  14:          return validationResult.Key;
  15:      }
  16:      else
  17:      {
  18:          return prefix + "." + validationResult.Key;
  19:      }
  20:  }

A couple things of note.  I'm using a C# 3.0 collection initializer on the dictionary here.  Then notice I'm using the "this" keyword to make ToMvcKey() an extension method.  Now I can change the original C# foreach loop to look like this:

   1:  foreach (var validationResult in validationResults)
   2:  {
   3:      this.ViewData.ModelState.AddModelError(validationResult.ToMvcKey(), null, validationResult.Message);
   4:  }

There are many ways to make this solution more flexible. For example, we could create an overload for our extension method that allows us to pass a dictionary in since different objects might be in different places of the object hierarchy depending on the ViewPage. In any case, the flexibility that the MVC framework gives you to perform various tasks many different ways is a great thing.


This Tuesday I'll be giving a presentation on ASP.NET MVC and Unit Testing at the CMAP main meeting: http://www.cmap-online.org/Meetings/Details/2008-10-07.aspx .


Wednesday, September 24, 2008 #

The jQuery Javascript library has gotten a significant amount of attention from Microsoft developers this year in large part to its nice fit with the new ASP.NET MVC framework.  I myself was totally new to jQuery and I started using it with MVC because I wanted to see what the big deal was.  Sure enough, I became a true believer like many others.  And I found myself suddenly having "JavaScript envy" because I couldn't do all the cool jQuery stuff in traditional ASP.NET (i.e., non-MVC) web applications.

The good news is that it turns out, it really is a simple thing to do to incorporate jQuery into a traditional ASP.NET web app!  Let's take an example.  I recently had a client with a requirement that when the user first come to a screen they wanted all the text boxes to be disabled (basically a read-only view).  They then wanted to user to click an "Edit" button and all the text boxes suddenly become enabled.

So often the default mind-set of a traditional ASP.NET developer is to write some server-side C# code to do something like this:

   1:  private void ToggleControls(bool enabled)
   2:  {
   3:      TextBox1.Enabled = enabled;
   4:      TextBox2.Enabled = enabled;
   5:      TextBox3.Enabled = enabled;
   6:      TextBox4.Enabled = enabled;
   7:  }

But there are a couple of problems with this approach.  First off, if I have 30 text boxes on this screen, that is some pretty ugly code to write. Sure, I could loop through the page's Control collection and programmatically set all the TextBoxes appropriately but what if I have drop downs or checkboxes?  Other than writing some IF statements, there no true elegant way to do this.  Secondly, you have to question why you're going to make a round trip to the server to do this sort of thing.

So let's say we approach this by using the Microsoft AJAX JavaScript library. We can make our implementation better by eliminating the round-trip to the web server by keeping everything in JavaScript like this:

   1:   var controlsEnabled = true;
   2:   
   3:   function pageLoad() {
   4:       $addHandler($get("btnToggle"), "click", toggleControls);
   5:   }
   6:   
   7:   function toggleControls(eventElement) {
   8:       controlsEnabled = !controlsEnabled;
   9:       $get("TextBox1").disabled = controlsEnabled;
  10:       $get("TextBox2").disabled = controlsEnabled;
  11:       $get("TextBox3").disabled = controlsEnabled;
  12:       $get("TextBox4").disabled = controlsEnabled;
  13:   }

Although this is better because we've eliminated the extra trip to the server, we're still stuck with the same problem that if we have 30 text boxes (and dropdowns, etc.) we have potential to have to write some ugly (or at least repetitive and boring JavaScript).

Now with jQuery this all becomes much more elegant.  One of the most powerful features of jQuery is that it allows you to easily select elements based on all kinds of different complex criteria by using jQuery Selectors. If you follow the link for the jQuery Selectors, you'll see that the possibilities are endless in terms of selecting elements by a combination of id, attribute matches, etc., etc.

The primary problem is that BOTH jQuery and the Microsoft Javascript library using the $ symbol as the global variable alias to the library. Fortunately, jQuery provides a simple mechanism to easily rectify this with the jQuery.noConflict() function. Now that we can use the full power the jQuery Selectors, we can essentially implement what was 30 lines of Javascript code with the Microsoft library to simple 3-lines of jQuery code:

   1:  var $j = jQuery.noConflict();
   2:  var disabled = true;
   3:   
   4:  $j(function() {
   5:      $j('#btnToggle').click(function() {
   6:          var disabledValue = (disabled ? "disabled" : "");
   7:          $j(":text").attr("disabled", disabledValue);
   8:          disabled = !disabled;
   9:       });
  10:   });

We alias the $ to be $j for jQuery instead. Now we can leverage jQuery any way we please and it can peacefully co-exist with the Microsoft JavaScript library.


There are lots of times when I want to do a "Clean" of my VS.NET solution.  Obviously, the most common way to do this is to right-click your solution in the solution explorer and select "Clean Solution".  However, there are 2 drawbacks of this.  One is that if you have files sitting in your bin or obj directories that are not in some way linked to your solution, they won't be removed.  Additionally, sometimes you just want to do a quick clean of a directory structure without having to fire up VS.NET.

You *could* use MSBuild to do this to avoid having to fire up VS.NET by doing a command like this:

MSBuild MyApp.sln /t:Clean

However, that still leaves you with the problem of leaving the orphaned files. 

I often just want to completely delete the bin and obj directories.  This might be because I want to ensure I'm truly starting fresh.  Or it may be because of have a little sample solution that I just want to throw into a ZIP file to upload or send to someone.  In that case, I want the bin and obj directories to not even exist.

I've found the easiest way to do this is to just use a little PowerShell function.  The function is called "cleanBin" and you simply pass a single command line argument which is the location of your solution root. It can be invoked by simply using this command:

PS C:\scripts> cleanBin C:\temp\SomeSolution

It will recursively look at every folder under your solution root and remove and bin or obj directories.  The complete function definition is as follows:

function cleanBin {
    param ([string]$path)
    
    write-host "Cleaning bin from: $path"
    get-childitem $path -include bin -recurse | remove-item
    
    write-host "Cleaning obj from: $path"
    get-childitem $path -include obj -recurse | remove-item
}

For re-usable functions like this, the easiest way to ensure that they are always globally accessible to you is to put them in your PowerShell profile file.  This file gets automatically run any time you start PowerShell.  You should have a folder inside your "My Documents" called "WindowsPowerShell".  Simply put a text file in that folder called "Microsoft.PowerShell_profile.ps1" and paste the above function in there.

Technorati Tags:

Tuesday, July 08, 2008 #

One of the best things about LINQ to SQL is that is really does have solid support for stored procedures.  However, it's not quite as friendly as dynamic LINQ to SQL with scalar values because you can't take advantage of anonymous types.  Instead you must return an actual known type.  Furthermore, this can't be a primitive so you can't return string or bool directly.  You also can't use a class that doesn't have a default (parameterless) constructor so that also rules out nullable types like Nullable<bool>.

Consider a trival stored procedure that looks like this:

   1:  CREATE PROCEDURE [dbo].[GetFirstName]
   2:      @ID int
   3:  AS
   4:  BEGIN
   5:      SELECT FirstName
   6:      FROM   Contacts
   7:      WHERE  ContactID = @id
   8:  END

We just want to return a single scalar string here. So we have to create a dummy class that looks like this:

   1:  public class DummyClass
   2:  {
   3:      public string FirstName { get; set; }
   4:  }

Then our DataContext method can look like this:

   1:  [Function(Name = "dbo.GetFirstName")]
   2:  public ISingleResult<DummyClass> GetFirstName(int id)
   3:  {
   4:      IExecuteResult result = this.ExecuteMethodCall(this, (MethodInfo)MethodInfo.GetCurrentMethod(), id);
   5:      return (ISingleResult<DummyClass>)result.ReturnValue;
   6:  }

And add to that, we'll need an extra consuming method that defensively checks for an empty resultset:

   1:  public static string GetFirstName(int id)
   2:  {
   3:      using (MyDataContext dataContext = new MyDataContext())
   4:      {
   5:          var result = dataContext.GetFirstName(id).FirstOrDefault();
   6:          if (result != null)
   7:          {
   8:              return result.FirstName;
   9:          }
  10:          else
  11:          {
  12:              return null;
  13:          }
  14:      }
  15:  }

So all this works just fine but it seems like a lot of work to go through just to get a simple scalar value from a stored procedure.  Not to mention that I don't want to have to go through this every single time I need a scalar value from a stored procedure in my app.  Visual Studio will essentially generate the DummyClass for me but what if I'm hand-crafting my LINQ to SQL and am not currently using Visual Studio code generation?  I don't want to have to go through that every time.  So what can we do to make this slightly more developer-friendly?

First off, I want to avoid code duplication if at all possible.  Not only if I return multiple scalars at different places in my app but also I'd prefer to avoid the duplication if these scalars are different data types (e.g., sometimes strings, sometimes Boolean, etc.).  What we can do is to create a simple generic class called Scalar that looks like this:

   1:  public class Scalar<T>
   2:  {
   3:      public T Value { get; set; }
   4:  }

This means I can re-write my DataContext method like this:

   1:  [Function(Name = "dbo.GetFirstName")]
   2:  public ISingleResult<Scalar<string>> GetFirstName(int id)
   3:  {
   4:      IExecuteResult result = this.ExecuteMethodCall(this, (MethodInfo)MethodInfo.GetCurrentMethod(), id);
   5:      return (ISingleResult<Scalar<string>>)result.ReturnValue;
   6:  }

So since I'm using generics here, I never have to write another dummy class again - regardless of whether I've got a string or Boolean or whatever.  I can always just re-use Scalar<T>.

Additionally, I had to write a consuming method that checked to see if DummyClass was null and if not return its value; otherwise return null.  Now that I know I'm always going to use the Scalar class for all my scalar queries, I can move this into a re-usable extension method like this:

   1:  public static T GetScalar<T>(this Scalar<T> scalar)
   2:  {
   3:      if (scalar != null)
   4:      {
   5:          return scalar.Value;
   6:      }
   7:      else
   8:      {
   9:          return default(T);
  10:      }
  11:  }

So basically, all I've had to do is create that trivial Scalar<T> class and that 1 extension method which consisted of 1 IF statement and now anytime I need a scalar value from a stored procedure in my app, it becomes as trivial as writing my data context method with the re-usable Scalar<T> and this:

   1:  public static string GetFirstName(int id)
   2:  {
   3:      using (MyDataContext dataContext = new MyDataContext())
   4:      {
   5:          return dataContext.GetFirstName(id).FirstOrDefault().GetScalar();
   6:      }
   7:  }

Now, the one catch - the one thing to notice here is that the property name in Scalar<T> is "Value".  That means that I'd have to change my stored procedure to alias my scalar data like this:

   1:  SELECT FirstName as Value

Although this is a downside, I believe it's well worth it in order to realize all the other benefits of quick implementation and avoiding duplicate and unnecessary code.


Sunday, July 06, 2008 #

At some point when creating a web app, you're going to want some reusable UI components.  This might be because you want the same visual UI snippet repeated more than once on a single page or it might be because you want to use the same component on multiple pages.  In a traditional ASP.NET web app, typically you would use a User Control for this type of thing.  In MVC you still have the option of using a User Control but you also have the option of rendering your UI snippet with a ComponentController.  So the question is, when do you use which?  There are pros and cons to each.

The most common scenario for a user control is that you pass in the Model from the containing view page.  For example, consider a AddressEditor user control that you use multiple times on a page to edit Contacts - once for Home address and once for Work address.  It might look like this:

<%=Html.RenderUserControl("~/Views/Home/AddressEditor.ascx", new AddressViewData(ViewData.Model.Contact.HomeAddress))%>

This is fine for those simple cases but what happens when you want your user control to have its own self contained logic?  For example, what if you're buildng a portal or a portal-like website where you want to have several self-contained "widgets" in your page.  You don't want the parent controller having to keep track of the models for 10 different widgets and then have to pass them in to each one.  A good answer to this is to use a ComponentController rather than a View user control.  A ComponentController can render its own views and the containing page can just look like this:

   1:  <div id="firstWidget" class="widget">
   2:      <%=Html.RenderComponent<MvcWidget.Controllers.WidgetCompController>(c => c.Widget1()) %>
   3:  </div>

In this case, the controller class basically looks like most any other controller class with the exception that it inherits from ComponentController:

   1:  public class WidgetCompController : ComponentController
   2:  {
   3:      public void Widget1()
   4:      {
   5:          IWidgetManager widgetManager = new Widget1Manager();
   6:          List<Foo> list = widgetManager.GetFooData();
   7:          RenderView("Widget1", list);
   8:      }
   9:  }

However, there still are some uses for view user controls here.  Let's say you want to render your widgets via an AJAX call.  One feature of the "normal" MVC controllers is that the views rendered can be either aspx or ascx.  Rendering an ascx user control from an MVC Controller would be a good choice when you want to implement the AJAX HTML Message Design Pattern where you're returning only an HTML snippet from the server rather than an entire page.  In this case, we can render our user controls with an AJAX jQuery call.  So if we had a couple of HTML divs (called "secondWidget" and "thirdWidget") and a WidgetController class with actions methods Widget2() and Widget3(), we could simply implement this simple jQuery function:

   1:  <script type="text/javascript">
   2:      $(function() {
   3:          $('#secondWidget').load('/Widget/Widget2');
   4:          $('#thirdWidget').load('/Widget/Widget3');
   5:      });
   6:  </script>

These are some rough ideas to get you started.  The complete code sample can be downloaded here.


Saturday, June 28, 2008 #

The latest release of the MVC framework provides the JsonResult for Controller actions.  I was surprised that I did not find a weatlh of examples for usage so I figured it shouldn't be too hard to get a decent example going.  It turns out, it was even easier than I anticipated.  I wanted to create an example where I would invoke an AJAX call to dynamically populate a dropdown list. 

jQuery has recently received a huge surge of interest of the ASP.NET MVC community so I've been getting up to speed on it myself.  I am quickly turning into a true believer and I've been impressed not only with how few lines of javascript it takes me to get things done but also how (relatively) easy it was to learn.  In addition to numerous examples on the jQuery web site I also recommend jQuery In Action.

Getting an AJAX request with jQuery and JSON in MVC is actually pretty simple.  The first step is to have a Controller action that returns a JsonResult:

   1:  public JsonResult GetStateList()
   2:  {
   3:      List<ListItem> list = new List<ListItem>() {
   4:          new ListItem() { Value = "1", Text = "VA" },
   5:          new ListItem() { Value = "2", Text = "MD" },
   6:          new ListItem() { Value = "3", Text = "DC" }
   7:      };
   8:      return this.Json(list);
   9:  }

Here I'm using the System.Web.Mvc.ListItem class (which is used as items in the SelectList) to simply return a contrived list of US states to populate a dropdown list.  All I have to do is call the Json() method passing in my object and it will automatically be serialized to JSON.  When the request is made the AJAX call can be seen in the Web Development Helper which is an invaluable tool to any AJAX development:

Notice the "application/json" in the request header and the textual representation of the JSON that is being returned from my JSON controller action.

The jQuery to make this happen is quite succinct:

   1:  <script type="text/javascript">
   2:  $(function() {
   3:      $('#btnFillList').click(function() {
   4:          $.getJSON("/Home/GetStateList", null, function(data) {
   5:              $("#stateList").fillSelect(data);
   6:          });
   7:       });
   8:       
   9:       $('#btnClearList').click(function() {
  10:          $("#stateList").clearSelect();
  11:       });
  12:  });
  13:  </script>

Notice on line #4 the use of the $.getJSON() jQuery method.  Then I've simply written a re-usable jQuery method called fillSelect() which will work on the JSON format returned by the ListItem class returned by my controller action:

   1:  $.fn.clearSelect = function() {
   2:      return this.each(function() {
   3:          if (this.tagName == 'SELECT')
   4:              this.options.length = 0;
   5:      });
   6:   } 
   7:   
   8:  $.fn.fillSelect = function(data) {
   9:      return this.clearSelect().each(function() {
  10:          if (this.tagName == 'SELECT') {
  11:              var dropdownList = this;
  12:              $.each(data, function(index, optionData) {
  13:                  var option = new Option(optionData.Text, optionData.Value);
  14:                  
  15:                  if ($.browser.msie) {
  16:                      dropdownList.add(option);
  17:                  }
  18:                  else {
  19:                      dropdownList.add(option, null);
  20:                  }
  21:              });
  22:          }
  23:      });
  24:   }

On line #13 above you'll see the strongly-typed "Text" and "Value" properties that I have the luxury of using because of the native JSON serialization into objects.

The complete code sample can be downloaded here.  It's barely 50 lines of code in all.


Sunday, June 22, 2008 #

To set a normal text box in the MVC framework, the most typical code would look like this:

   1:  <%=Html.TextBox("FirstName", ViewData.Model.Contact.FirstName)%>

The key here is that you should set the name of the textbox to be the exact same name of the property name.  If you do this, then it enables you to use extension methods such as the UpdateFrom() method to automatically populate your object from Request.Form parameters when you post to your controller action.  This is all well and good but it is very easy to make a typo when typing the "FirstName" string for example.  Wouldn't it be nice if this all just happened automatically? 

Well, I found a very elegant solution to this last week when I was browsing the latest code of the Validation Framework on CodePlex.  In the MVC quick start code for the Validation Framework, they provide extension methods for creating a "ValidatedTextbox", for example, that works with that validation framework which looks like this:

   1:  <%=Html.TextBoxValidated(() => ViewData.Model.Product.ProductName)%>

Not only is this solution elegant but I quickly realized that this could be easily generalized to so many other scenarios.  Not just in the context of this validation framework but also for creating the most "normal" textbox scenario.  By using this method, I can now re-write the first example like this:

   1:  <%=Html.TextBox(() => ViewData.Model.Contact.FirstName)%>

The resulting HTML that is produced will populate the textbox with the value from the FirstName property and it will also name the textbox "FirstName".  So the HTML the gets rendered in the browser is:

   1:  <input type="text" name="FirstName" id="FirstName" value="Bill" />

It turns out that there is not many lines of code required to pull this off.  The lambda expression is specified in the mark up and a Linq Expression is used for the method parameter.  The complete code for the Textbox extension methods is as follows:

   1:  public static class ControlExtensions
   2:  {
   3:      public static string TextBox<T>(this HtmlHelper htmlHelper, Expression<Func<T>> expression)
   4:      {
   5:          return TextBox<T>(htmlHelper, expression, null);
   6:      }
   7:   
   8:      public static string TextBox<T>(this HtmlHelper htmlHelper, Expression<Func<T>> expression, object htmlAttributes)
   9:      {
  10:          MemberExpression memberExpression = expression.Body as MemberExpression;
  11:          if (memberExpression == null)
  12:          {
  13:              throw new ArgumentException("The specified expression is not a valid MemberExpression.", "expression");
  14:          }
  15:   
  16:          Func<T> compile = expression.Compile();
  17:          T value = compile.Invoke();
  18:   
  19:          return htmlHelper.TextBox(memberExpression.Member.Name, Convert.ToString(value), htmlAttributes);
  20:      }
  21:  }

Notice that since this is a MemberExpression where we're just getting a value from a property, we can simply use the Member.Name to get at the "FirstName" string.  And then we can use the Compile() method of the Expression<TDelegate> class to get executable code in the form of a delegate that represents the lambda.  Now that we have the Func<T> we can simply call Invoke() to get at the value of the FirstName property.  Now that we have the name and value, we can pass it to the already existing TextBox extension methods.

This technique can really be generalized to any MVC control.  It can also be generalized to create composite controls as they have done in the Validation Framework above.  In my opinion, Microsoft should consider including this type of thing in the base MVC library.  But if not, it's easy enough to add to your own MVC helper libraries.