Debugging versus Testing (MVC, Web 2.0)


I have been playing with ASP.NET MVC lately and I hvae noticed one interesting artifact of the methodology, at least for time being. WIth ASP.NET, you have a good debugging experience. With MVC, you have a good testing experience.
 
This is not a blanket statement, of course, as debugging is quite easy in MVC, as long as you are in the controller. But, consider the following scenario (yes, I will give the solution to this problem, as well).
 
You fire up the MVC Membership starter kit. You hook it up to SQL Server (blog entry here). You are now able to log in. Go to change password and you end up with a NullReferenceException on this line (highlighted)
 

<script type="text/javascript">
/* <![CDATA[ */


  function starterKit_mvc_membership_validateChangePassword()
  {


    var pwd_minChars = <% =(int)ViewData["MinimumPasswordLength"] %>;

Nothing really stellar here. This is just a bug in the software. Normally, when you find a bug like this, you would go to the call stack and find out what the calling member was sending in. You would also get a good spot to set your breakpoints. This is not as straightforward, however, in MVC, because the call stack is pretty much non-existent once you are filling the view. You cannot step back into the controller and find the reason for the error.
 
In the future, Microsoft may have a solution for this. For now, you have to work with the new way of thinking and do a bit of investigation. Since this is the PasswordChange view in the FormsAuthentication folder, I am looking for hte FormsAuthenticationController. The code is not here, however, because it is a derived class.
 

public class FormsAuthenticationController
    : StarterKits.Mvc.Membership.Controllers.
BaseFormsAuthenticationController

 
So I set my breakpoints in the BaseFormsAuthenticationController instead. Line 709 yields the answer (or rather line 709 and scouring the entire PasswordChange() routine yields the answer). The only thing in ViewData is a Boolean:

// success!
ViewData["Success"] = true
;
return RenderView( "PasswordChange" );

The code ran perfectly and my password has changed, but I am still treated with an error trying to fill the JavaScript on the form. NOTE: Will hit possible solutions later.
 
The problem here is not Troy’s code, it is the experience. We all end up with bugs in our code as we write applications. In fact, we expect bugs as we code, and that is why test driven development is so important. It helps us find the bugs quickly. The problem here is a disconnect between the UI bits and the backend. And, it is not unique to MVC. A few weeks ago, I blogged about clashes between ASP.NET AJAX and the MapQuest tiled map API. I have also had issues with over engineered CSS clashing with CSS packed with controls.
 
The debugging experience on the client is very rudimentary at the present time. And, there is a huge gulf between backside debugging and client side debugging. In general, I find myself using Firefox a lot when I am working with server code that outputs client side code. Currently, Firefox has the best client side debugging tools, which leaves a huge opportunity for Microsoft, as these tools cannot adequately link the two disparate parts of the Web 2.0 application in a single debugging environment. To be fair to Microsoft, they have tried with Visual Studio and Internet Explorer. If you flip off the Disable Script Debugging checkbox, you can end up with some JavaScript debugging goodness. But, you are still debugging one set of code in isolation, even if you are using the same tool.
 
I wish I had an answer on how to solve the problem. While we want a debugger that allows us to go through the entire chain of events, it gets rather complex to link views to controllers in the debugger. It is even more difficult to follow code from server side to the client side. I am optimistic that it is not impossible, but wonder if it is possible without further bloating the development environment to the point that the experience is degraded.
 
Silverlight overcomes this problem, to a large extent, as the code is all .NET. There are still some gotchas, but you have a clean separation of client and server in Silverlight … at least if you develop the server end like a service. Software as a Service – what a unique concept! Wink MVC has the ability to overcome this problem, as well, but is a bit more complex as views are not running the code in a traditional sense. The separation is also NOT clean, at least not in the plethora of examples on the web. The same is true with web 2.0 technologies, although they are maturing a bit and people are getting the SOA/SAAS idea.
 
I am sold on the TDD aspects of MVC. As I have stated before, I am not sold that it is the only way, but MVC really does force separation of concerns. I am not sold on the current view model, especially with views peppered with ASP like code. I am sure that will change over time once the Framework understands all of the fundamental controls.
 
Now, back to the problem at hand, since somebody will ask if I don’t spout off. My first thought is one of two solutions:
  1. Create the JavaScript completely server side and inject it
  2. Flip to a different view for confirmation

#2 will be easier, but I need to solve #1 regardless to use the tiled maps (MapQuest currently) in MVC. An injection type model is easier to debug, as all of the code is server side until it is placed on the page. It does lead to having to test the UI to get the bits down and completely debug the solution, but a view of tags and code leads to the same issue. At least with an injection of client side code model, I can debug the JavaScript separately from the code that builds it. Smile

Peace and Grace,
Greg

Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: