Razor is sharp, but NHaml is still haiku for HTML 5 and JQuery

A colleague of mine told me recently about Razor, the view engine for ASP.NET MVC 3, and upon researching it and using it in a test project, I almost instantly came to compare it to NHaml since I’ve been using HAML for several years doing rails on the side. What I found is that though Razor is the best view engine I’ve seen from Microsoft (on top of a great version 3 of ASP.NET MVC – nice job guys), I still believe NHaml’s syntax is significantly better suited for HTML applications and even more so if they use JQuery.

Though Razor does a great job requiring minimal characters to insert executable code logic in between the markup it generates (and is basically equivalent in that respect to HAML), it does nothing for minimizing the amount of code you have to write to express the HTML outside of those logic statements. NHaml is simply superior here when you are generating HTML for this reason: it reduces markup to the minimal information needed to identify the JQuery or CSS selectors that elements have applied to them.

It does this because with NHaml normally you specify the name of an element without the angle brackets, but if the tag you want is a DIV element with an ID attribute, you can just specify the ID prefixed by a hash symbol and drop the DIV altogether.

<div id=”blah”></div>

becomes:

#blah

This also works for CSS classes. This dramatically increases code readability because lines of code begin with the JQuery selector or CSS style name used to access them. When writing Javascript or CSS, locating these elements in markup is much easier. This is already on top of the fact that NHaml drops the requirement for closing tags.

Here’s an example that I think illustrates the point. Let’s say I have a CSS style sheet with the following styles. Don’t worry about the attributes in the styles themselves just look over the list of CSS selector names (container, banner etc.) and think of looking at this file day to day:

#container { width: 100%; }
#banner { background-color: blue; } 
.topic { font-size: 14pt; }

Now here’s some HTML markup styled with selectors in the above sheet in HAML:

#container
  #banner

    .topic Hello

Here’s how you would generate the exact same markup using Razor:

<div id=”container”>
 
<div id=”banner”>
   
<div class=”topic”>Hello</div>
 
</div>
</div>

Building on this let’s say we wanted to override the .topic style inline with some other styles, and throw in some inline JavaScript. Here’s HAML again:

:css
  .topic { font-size: 14pt; }

:javascript
  alert(‘hello!’);
#container
  #banner

    .topic Hello

and here’s Razor:

<style type=”text/css”>
.topic { font-weight: bold }
</
style>
<javascript type=”text/javascript”>
alert(‘hello’);
</javascript>
<div id=”container”>
 
<div id=”banner”>
   
<div class=”topic”>Hello</div>
 
</div>
</div>

Hopefully you can see the HAML is much easier to read, and reduced in lines of code by about 15% in this example.

Here’s another great post from late last year that shows some comparisons of Razor and NHaml.

Using LABjs to get AJAX-loaded ready callbacks

I discussed in my previous post a function I’d came upon through searching that allows HTML that is appended to the DOM through AJAX which includes SCRIPT tags to wait until they have loaded before firing ready events. Upon testing it in Firefox, I found that it wasn’t working in some scenarios, so I began searching again and found LABjs. LABjs stands for Loading and Blocking JavaScript and allows you to chain loading of scripts together and end that chain with a function that gets called back. The nice thing is you can choose to use the word “wait” between load methods and it will block before loading the next, or if you omit the wait, the scripts will load in parallel, speeding up load time of your web application.

Here’s an example. Let’s say you have a site that loads a partial section of HTML from an AJAX request and you’re going to append it to the page, but it includes some scripts in it. Your script is dependent on two other publicly hosted scripts (twitter, Google maps for example) and can’t execute until those are finished loading. Rather than load them in your main page and increase startup time, LABjs handles it perfectly:

Old AJAX response HTML:

<script src=”http://publicwebservice1.com/script1.js” />
<
script src=”http://publicwebservice2.com/script2.js” />
<!– This can’t execute until the first two scripts have loaded, but not all browsers load these in order in a dynamic update to the DOM! –>
<script src=”myscript.js” />

Old myscript.js contents:

<script type=”text/javascript”>
$(document).ready(function() {
// This will fail if the first two scripts haven’t loaded yet
var script1Object = new PublicWebService1.APIObject();
var script2Object = new PublicWebService2.APIObject();
}):
</script> 

Replacing this with LABjs becomes:

<script type=”text/javascript”>
$LAB
.script(http://publicwebservice1.com/script1.js&#8217;)
.script(http://publicwebservice2.com/script2.js&#8217;).wait()
.script(‘myscript.js’).wait(function() {
var script1Object = new PublicWebService1.APIObject();
var script2Object = new PublicWebService2.APIObject();
});
</script>

Accessing dynamically loaded scripts with JQuery via AJAX

I’ve been working on a side project in rails that uses AJAX for all posts to the server with JQuery BBQ as state management (using the hashchanged event to provide bookmarkable views) and ran into a problem that can happen to anyone using JQuery. When AJAX calls are placed, they often retrieve HTML that contains script tags in it and then place this HTML into the calling page’s DOM. The problem is that usually one can use JQuery’s ready event to wait for the document to finish loading before accessing objects in those scripts. However when a Webkit based browser (such as Google Chrome) loads this content, it doesn’t wait for the scripts to load before firing the ready event. In my case I was implementing ReCaptcha for image verification of users signing up for my site and the JavaScript provided by them was getting inserted into my registration page via AJAX.

After massaging Google keywords to find the right query and paging through several results, I found a post with a great solution. Basically this code parses your HTML on the client for script tags and loads them separately before returning from the function. I’m now using it anywhere I inject code into the page that has SCRIPT tags via AJAX.

The Minimalist Development Movement

Over the past 11 years, .NET technology, fueled by Microsoft’s ability to deliver sophisticated development tools, has arguably ruled the enterprise business software landscape. Intellisense, drag-and-drop UI design, XML configuration, dependency injection, unit testing, IDE extensibility APIs for third party controls, continuous integration, and more attempt to ease the use of Agile and SCRUM processes as the Visual Studio IDE supports more and more of these features through wizards and templates. .NET started as a better version of Java, and as such inherited many of the powerful capabilities, but also limitations in that development and deployment approach.

However in the past several years a move towards a minimal development tool mindset has started to occur. This is made possible by the creation of more sophisticated frameworks that establish conventions and set constraints on how to go about implementing things. These constraints reduce the number of API calls to remember, and the number of front end technologies that a typical developer needs to be fluent in. As a byproduct, the required capabilities of development tools is also reduced. Rails, which led to ASP.NET MVC, and JavaScript technologies like the MVC framework being built on Coffee Script as well as mobile frameworks like Titanium Appcelerator all take this approach. They provide the framework and API, and you use the development tool of your choice. Because the framework limits what you can do, but elegantly provides 80% of what you need in most applications, you don’t need an IDE that does so much for you. Extreme minimalists use VIM, Emacs, or TextMate; and Aptana is a popular one with first class support for CSS, HTML, HAML, Rails, JavaScript and many other minimalist technologies that might be a little more approachable to a seasoned .NET developer.

Visual Designers for 20%

However, to take part in this new shift requires a different mindset. What if you had to do all of your user interface development without graphically previewing it first? A dirty little secret in many Microsoft shops is that we rarely use the UI designers anyway. Clients and customers are always asking for features that negate the productivity enhancements touted by RAD design, and force us to the code to do more sophisticated things.  I’ll argue that this is due to an inferior separation of concerns in ASP.NET, and not simply because you’re doing something more complicated. If your framework requires you to break patterns to do something complex, how good of a framework is it? When a development tool only really shines for the minority of projects, your on the losing end of the 80/20 rule. When you design tools to focus on letting developers visually design things, you are continuing to treat UI assets as single units that encapsulate their behavior, presentation, and data. Modern frameworks that separate these concerns make it difficult (if not impossible) to visually represent things as they appear at runtime, but the tradeoff is an increase in productivity due to patterns that decouple responsibilities.

Interpretation vs. Compilation

What if you don’t compile your project to test it out? There are legitimate applications that require compilation due to performance constraints. But if quality is the concern, the efficiency enhancements afforded by these frameworks coupled with a disciplined automated testing approach negate this concern.

Document what you’ve built instead of what you want

What if you don’t create requirements documents, but rather rapidly implement and write tests to serve as the documentation for what the system currently does? We already know from years of SCRUM and Agile debates that documenting a system up front more often than not results in bad designs, slipped deadlines, and stale documentation. Most customers and clients are not system analysts and as such can’t be expected to communicate all of their needs on the first try. A picture is worth 1000 words, and we’ve all been in the meeting where the customer advocate is shown what was built based on their design and they realize things missing that they didn’t communicate. Doesn’t it make sense to use a development process that encourages and adapts to this situation instead of fighting it?

Contrary to popular belief, to pull this off one needs to be a better developer, who follows patterns even more than before. Developers also need to communicate with stakeholders more, and incrementally deliver *tested* features. Increasing the ability for a developer to communicate has all kinds of other benefits as well, such as the ability to clarify requests, think outside of the box, and generally be more pleasant to work with.

If the thought of letting your tests provide your documentation sounds crazy, tell that to Sara Ford.

Get better at learning your framework instead of fighting it

We’ve all been in the code review where someone implemented an API call that’s already in the .NET framework. If we’re honest with ourselves as developers, we really don’t keep much of the .NET technology stack in our head, we just know how to use Google well. If we were able to reduce the number of patterns and APIs used in our solutions, we could retain that knowledge and know the best way to leverage the framework to do what we need to do instead of fighting it. ASP.NET MVC and Rails both exhibit this, and I’ll argue Rails does a better job. ASP.NET MVC won’t complain if you make the mistake of trying to throw a bunch of logic in your view, where in Rails you really have to fight the framework to instantiate classes here. As DHH says “constraints are liberating” (start at 3:50 in).

The challenge

If you could challenge yourself with one technical hurdle this year, would you rather learn another API? Perhaps a way to interface with a new business system? Or would you rather experience a shift in your approach to development that has long lasting, measurable effects on your ability to deliver rapid value and makes you more attractive to established companies and startups? To do so requires several things.

  1. Approach these new patterns and capabilities without attempting to compare them to existing methods. As humans we love to do this, but often we get caught up in analysis paralysis or think we’ve “got it” when we grasp just one of the many innovations in these newer frameworks.
  2. Do not declare competence with these frameworks until we’ve actually grasped them in their entirety. Learning Rails without understanding caching, convention based mocking of tests, or the plugin architecture is like learning C# but ignoring generics and lambda expressions.
  3. Don’t try to figure out how to shim legacy .NET patterns into these frameworks. You wouldn’t expose a low level communication protocol through a web service or REST API where clients are expected to allocate byte arrays, so why would you expect to figure out how to host a third party ASP.NET control in MVC or access a database using T-SQL from an MVC view. Sure, you can do it, but you’re missing the point. And that is to embrace new patterns and learn to abstract the old way of doing things. We’ve been doing it with .NET for years, now let’s see if we can do it when legacy .NET patterns are what we’re abstracting.
Follow

Get every new post delivered to your Inbox.

Join 75 other followers

%d bloggers like this: