Life, Surf, Code and everything in between

Amazon Kindle on the Road



Wireless Access

So I broke down and got myself an Amazon Kindle Reader last week before I left for an extended trip to Europe. I've been reluctant to spend this kind of money ($399) on an electronic reader, but since I'll be spending a good deal of time on the road this year in Europe I thought it'd be a good idea to stock up on reading material before I hit the road and not have to deal with keeping stacks of paper books with me.

I read a lot of books - fiction, non-fiction and technical - and other than the technical books I really have no need for physical books on a shelf somewhere. In fact, more often than not, once or twice a year I dump all of my books on our local used book store and get nothing back from the original value anyway other than bestowing a bargain (or curse) on somebody else on my bad taste in books.

After using Kindle for the last week and a half extensively I can safely say that I'm happy with this purchase. The reading experience of the device is great and it works well in all of my reading scenarios. Since I've bought it I've probably put 15 hours of reading in and I have run the battery down to about half. That is though with the wireless off since I'm in Europe now where the Whispernet feature that connects the Kindle to the Internet and provides the instant online buying and downloading of books, doesn't work. Here I can still get books but I have to download to my machine and then sync to the device.

I did use the wireless feature though before I split and downloaded about 10 books. I was surprised to see that book downloads are pretty darn fast with most books completely downloaded after a few minutes. In fact, I was at Powell's at the Portland airport browsing around, found a couple of more books, dug out the Kindle and by the time I walked out had the books already downloaded. Kind of a bummer for Powells though (but then they're way overpriced anyway <g>).

From a feature perspective I love the device for the thing it was designed for reading and readability. Tonight, I missed a late bus today here in Geneva and was stuck at a bus stop for a half an hour in low light. Even though the device isn't backlit I was comfortably reading my book by the street light half a block down. The half an hour flew by and I almost missed my bus not paying attention. <g>

Although the device won't win any awards for product design it's functional and the screen just works great. I was reading for most of my 9 hour trans atlantic flight and there's none of the eye fatigue that comes when reading content on a laptop screen.  I read frequently in bed before going to sleep (if for nothing else than to get my mind of code before going to sleep) and while eating. Eating is probably the 'oddest' place for reading in general and Kindle actually works better than trying to get a book spine to behave. There's the issue of green spinach stains though... Hmmm...

You can search and bookmark easily and even annotate. There's internet access to WikiPidia and a few other select sites, but don't expect to get free WiFi out of the Amazon paid connection. Part of the high price is probably meant to defer Amazon's wireless bill for Whispernet that runs over Sprint's high speed cell network and allows for book browsing and the limited focused research Internet access.

Selection

Book selection is good but certainly not all inclusive. I was looking for some fairly new Sci Fi books, and found they weren't available while last releases by the same authors and publishers were. Seems odd - I suspect publishing to Kindle goes by the paper back rule - once paperback comes out it can also go to Kindle. Opportunity missed if books can sold electronically at near hardcover prices until then <shrug>

But most fiction and non-fiction books I was looking for were available with Kindle.

The technical book selection for Kindle is  pretty sparse though - it looks like only some of the big publishers like Sams, Addison Wesley etc. are putting out Kindle editions at the moment. But some of the more prominent 'design', 'architecture', patterns etc. books can be found for Kindle, which is actually a good fit. I picked up a new copy of Pragmatic Programmer which I'd been meaning to get anyway, but was bummed to find that Code Complete and Design Patterns (which are good to have around) weren't available. OTOH, I'm not sure how well I'd like to have highly technical books in this electronic format - I still prefer a physical book for reference books believe it or not (if for nothing else that they are separate from the computer screen which is already massively overloaded with simultaneously running applications). Actually I'm just checking back and see that a few of the big hits are available. I guess I wouldn't mind having a portable copy of Stephen Walther's ASP.NET 3.5 book or Adam Nathan's WPF book with me at all times and those can actually be had for Kindle, but looking at some of the samples of Stephen's book it's not as user friendly as I would hope. Code listings split badly and in the case of Adam's WPF book you lose all the color and good flow that that book sports. This one page electronic format is just not a good match for books that contain lots of code I think. I still prefer a printed book for real reference work I guess (yes even over purely online content which is always so damn scattered).

But for pure printed text - the reader works as well as a printed book.

Talk of the Town - whatever!

While I was flying the Kindle also got a lot more attention than I liked - people would walk by the aisle and stop and  constantly ask what it is, how it works etc. After a while I got tired of that shit and put on my headphones and appeared to be really immersed in my reading. Can I never get any piece and quiet? The book reader also came up in a few conversations I've had here and several very unlikely folks got really excited about the device and its possibilities including one real grouch <g>. People who read a lot are immediately taken by the idea of having much of their reading material at their finger tips.

The device is not pretty, it has hard edges and the buttons for pages while adequate are too big and to easily clicked or bumped resulting in double page turns. But it's quick to get used to. Overall I'd say the device is practical, but certainly not flashy both in external design or the screen UI. That's probably a good thing - it helps  from getting too distracted and keeps me focused on its primary task: reading a goddamn book instead of playing video games.

Remember it's an Amazon Sales Machine

So the Kindle is a good deal for me - I have one thin device I can carry around with me and carry many books which is great for travel. But it's expensive. If it wasn't for my extended absence I probably wouldn't have bought this thing. $400 is not cheap for what amounts to a big Amazon sales tool. The device is locked to Amazon, so everything you get for it has to be bought through Amazon. This means no used books discounts or even buying books from other sellers at Amazon. And even though there's no physical product prices are only slightly less than full shipped books. Given that Amazon ships most physical for free (if you're willing to wait a little) it's kind of a bummer that there's not more of a discount for Kindle purchases either. Kindle is clearly targeting the geek and well to do set with this device. Surely both publishers and Amazon are laughing all the way to the bank for each Kindle book sold.

Maybe someday there will be an open and actually widely used e-book format that doesn't suck and has enough support from publishers, but at this time the Amazon Kindle seems to have that market cornered. While other solutions exist they are either infringing copyright laws or are relying on minimal support from a few independent publishers here or there. Things in this space will likely change in the future - Amazon has proven that people are willing to pay for the hardware to get electronic book content, but it's hard to say which way this will go.

Still I'm happy with the device if for nothing else than having one thing to schlep around instead of a 5 books as I often did  when gone for longer stretches of time...



ASP.NET Connections Slides and Samples Posted



I've posted my session slides and samples from my ASP.NET Connections sessions last week in Orlando. I did three sessions at the conference and you can check out the slides and samples here. All three sessions had extensive samples (and I didn't even get to them all) so if you attended my sessions be sure to take a look at the samples as there's lots of extra stuff that didn't get covered in sessions.

The files posted here are more current than the original code and slides provided at the conference and the immediate updates I posted. I spent a little more time cleaning up a few dependencies, hopefully making it a little easier to get the samples running. Please be sure to read the _readme.htm files (or the Configuration links on the default page) in each of the projects, as they include important information about set up to run the samples and setting up the databases.

Here are the links and summaries of each of the sessions:

Ajax Alternatives: Using jQuery with ASP.NET

This was by far the most fun session for me, partly because I've been working with jQuery so much in recent months, but also because it was a really interactive session. I started this session with a basic ASP.NET page and went through the motions of adding jQuery functionality to the page. In 10 minutes of hands on building up of the page I went through a wide cross section of jQuery from selector syntax to document manipulation, to special effects, using plug-ins and  creating an plugin. From there the session has samples that demonstrate basic Page based AJAX operation - Ajax without any sort of framework on the backend, followed by examples and some generic helper code that lets you use WCF 3.5's Ajax support with jQuery. Samples include demonstrations of HTML loading, using server based HTML templating (ie. poor man's UpdatePanel like behavior) and raw data results with JSON. The WCF examples provide mroe data driven examples which demonstrates the same examples, but using purely client side manipulation of the DOM with data from the server. The two examples use a stock quote server and portfolio display that is rendered and updated client side including a nice interactive display. I also showed a cool photo album application that shows off a few useful plug ins including sortables and an inplace editing component I created for doing real time and in place  data updates using the DOM as the data storage mechanism. Finally there is an example of a jQuery component (jquery.ui's DatePicker control) wrapped as an ASP.NET control for easier usage in the ASP.NET environment.

The photo album application is running on my site here:

http://www.west-wind.com/rick/photoalbum/

and a demo that allows access to the admin functions the demonstrate the more interesting features can be accessed at this particular URL:

http://www.west-wind.com/rick/photoalbum/demoMaui2006/Default.aspx

(this demo likely will get trashed by vandals since it allows user input and I'll probably pull it after a few days or so, so check it out now while it's there)

You can download this session from:

http://www.west-wind.com/files/conferences/jquery.zip

 

WCF 3.5 JSON and REST Services

This session's focus is on the new WCF 3.5 HTTP features that provide support for REST principles and AJAX support. WCF 3.5's AJAX support has been made nearly as easy and comprehensive as ASMX functionality and there are many options of how data can be accessed over HTTP now with official protocol support for the webHttpBinding. This session starts of with examples of pure REST URLS and demonstrates features like URL templating, different response formats (wrapped, bare, XML, Json) as well as the various different options for serving in this fashion. THere are also examples of serving up raw data such as images or HTML content out of the REST based API. The remainder of the session focuses on AJAX functionality and explores different ways that WCF services can be called. There's a comprehensive Stock Service example that shows simple stock quote retrieval, a more complex portfolio manager and streaming stock history graphs to the browsers. Examples are provided for using Microsoft ASP.NET Ajax as a client as well as jQuery as a client in order to avoid loading of Microsoft Client Libraries.

You can download this session from:

http://www.west-wind.com/files/conferences/wcfRest.zip

 

Building a LINQ to SQL Business Layer for ASP.NET Applications

Focus of this session is on a LINQ to SQL Business object framework that wraps LINQ to SQLs data access model. LINQ to SQL - although completely object based, is still little more than a sophisticated data access layer and so a business object layer is still needed to abstract business logic and provide common functionality that every business related entity requires. THe business layer provides a few high level abstractions to the CRUD layer as well as a host of low level features that allow better control for low level data access in case LINQ to SQL queries are ill suited for queries and operations that cannot be performed with LINQ to SQL at all. This session includes a simple but comprehensive Time and Billing example application that demonstrates many aspects of working with LINQ to SQL using this business layer.

This is an update to previous versions of the LINQ to SQL Business layer I've put out. Enhancements in this version include removal of the requirement for tables to have timestamp fields, several enhancements to dynamic expression usage internally and a few small bug fixes.

You can download this session from:

http://www.west-wind.com/files/conferences/LinqtoSqlBusiness.zip

 

Hope you find some of this stuff useful.



Reusing old Laptop SATA Drives via USB



As I'm about to head off to the airport for an extended 3 month travel gig in Europe, I'm doing my last minute backups to DVD and hard backups onto my desktop backup drive.

I am rummaging through all of my stuff in my travel bag and  I just remembered that I always carry a spare SATA drive with me - just in case something blows up so I at least don't have to run to the store to get a new drive (and yes this always seems to happen at the most inopportune time for me!). This is an old drive, bought to test some OS or VS beta long ago. The data on the drive is pretty stale (just checked it's from early 2007 - pre Vista even) so the content is not important.

But I figured I can put that drive to use as a backup device. So I got out my trusty SATA to USB interface cables and did a fairly full back up right onto this spare drive. USB to SATA cables are readily available these days and the make it easy to reuse an old drive.

There are tons of cables available that do this but I use this one and it works well for me with or without power:

SataDrive

There are a variety of these cable adapters available and you might want to read reviews on all of them to find the right one. The CoolMax I have seems to have a few bad reviews at Amazon, but it's been working fine for me for a few years with several drives I've attached to it, although I have a much older version of it and one that came with an optional power adapter. One thing to look for is a package that also includes  a power adapter.  In the past I've had problems with only the USB cable powering even the laptop drive. For desktop drives the power is definitely needed in most cases (depending on the power output of the USB bus). The cable above fits SATA, and standard IDE drives which is a bonus if you need to work on an old drive. On my current machine the power adapter is not necessary with the laptop drive attached which is nice - only need the one small USB cable with the adapter at the end.

Beyond travel these converters are useful if you run into problems with a drive. I've used this to pull data of several other people's drives once it's come out of their machines where the drives wouldn't work usually due to some boot corruption.

For me and for travel what's nice about this setup is - especially if it works without power as it does on my laptop - that you can get faster and smaller raw drives than the typical pocket USB drives you buy. Pocket usb drives tend to be slower 5400rpm drives while most of us have 7200rpm drives in our machines. This certainly makes some performance difference especially for doing backups. And because it's a raw drive you can plug it into your machine should the primary drive take a dump so it is real spare.

I probably wouldn't recommend this approach for a second dedicated drive that you use all the time because a raw drive is - well - a raw drive sitting on your desk <g>. But for an occasional backup device,when already carrying around a spare hard disk, this great. 1 small cable to carry in addition to the drive is a small price to pay.



jQuery.ui Sortable



Sorting of a list of items is a common task in any user interface. Personally I've been wanting to add sorting to a number of applications for ages, and some time ago I started down the path of building something of my own to handle this task on the client side with JavaScript. Ok, I failed - I got most of it almost working but there were always  a few things that just didn't work quite right. I've also tried a few other components that do sorting and most are quirky or don't work well cross browser.

[updated 4.28.2008 - added code to show how to notify server of sort updates]

jQuery's Sortable is a cool client side jQuery plugin that is part of the jQuery.ui plug in library that works well, looks very nice and is fairly self contained (2 scripts beyond jQuery). It lets  lets you create sortable unordered/ordered lists or a plain group of contained DIV tags.

It's extremely easy to use in client code by simply pointing at the list and a few options to make the list sortable. Items can be dragged around and sorted and the items appear transparent when dragging (by default). It's also fairly customizable to let you control how sorting works and how the items are represented while dragging.

One place I used Sortable is in my photo album where I allow client side sorting of the images that are displayed. In my app the administrator can rearrange images in real time, make changes to captions and then when done save them back via an Ajax callback to the ASP.NET server app.

Here's what sorting operations look like (the real deal is a lot smoother - this is captured as an animated gif with CamTasia):

Sortable

Items slide around as they are sorted and use a nice sliding into place effect when dragging is complete, or slide back into their original position if moved out of the main area. The plug in also handles scrolling the browser when bumping up against edges. The really cool thing about Sortable though is how easy it is to use: It's an extender, so all you do is point it at the result of a jQuery selector that is a list and add a few simple and optional settings and that's it.

To use Sortables you'll need jQuery plus a few of the jQuery.ui scripts:

<script src="/photoalbum/scripts/jquery.js" type="text/javascript"></script>
<script src="/photoalbum/scripts/ui.base.js" type="text/javascript"></script>
<script src="/photoalbum/scripts/ui.sortable.js" type="text/javascript"></script>

All the code required to make the above list sortable is:

$("#ulThumbnailList").sortable(
    {  opacity: 0.7, 
       revert: true, 
       scroll: true , 
       handle: $(".imagecontainer").add(".imagecontainer a img") 
    });  

The settings parameter object is optional but allows configuration of the behavior for the sorting/dragging operation. Here I optionally apply opacity, and tell the sort to revert to original position on aborting and scrolling the browser window when bumping against the edges. In addition, I supply a selector to use as a drag handle - the item is dragged by grabbing the image container which is a DIV that wraps the image. The above control supports in-place text editing and selecting the entire control makes it hard to get the text editing to 'take' because the control will try to drag fairly quickly.

Notice the handle selector: You can apply a selector for the area that acts as the drag handle - ie. where the user can drag the item. Here I want it to be a DIV tag that wraps the image. Note that I also select the image itself - the drag handle is very explicit about which element is used so I make sure that both the container and the contained image can initiate drag operations. (this is a change from the previous rev I'd worked with).

Keep in mind that Sortable doesn't work with tables, but HTML lists or a set of Div tags, so if you need a table like layout you need to think of other ways to arrange the layout. You can use a Repeater or ListView in ASP.NET to create this sort of layout easily. The above HTML uses contained plain old <li> tags with a fixed width and float:left to provide the 'column' based layout of the photos.

The trickier part - for the photo list above at least though - is getting the CSS right.  The above is rendered as an unordered list with float:left items which gives the effect of a table. Note that Sortable can sort elements in this way and does the right thing when sliding elements out of the way as the dragged item moves through the table - it's a very cool visual as well as practical effect.

The unordered list HTML above is rendered like this:

<ul id='ulThumbnailList'>
    <li id='f0db40f3' class='photolistitem'>
    <div class='imagecontainer'>
    <a href="javascript:ShowImagePopup('f0db40f3');">
        <img src='tb_sweatshop.jpg' class='thumbnailimage' id='f0db40f3Img' title='sweatshop.jpg' />
    </a>
    </div>
    <div id='f0db40f3Notes'>Team programming
    </div> <div class='deletethumbnail'>X</div>
    </li>
 
    <li id='64ac6f8c' class='photolistitem'>
    <div class='imagecontainer'>
    <a href="javascript:ShowImagePopup('64ac6f8c');">
        <img src='tb_whalewhispers.jpg' class='thumbnailimage' id='64ac6f8cImg' title='whalewhispers.jpg' />
    </a>
    </div>
    <div id='64ac6f8cNotes'>Can you hear me now? Really now?
    </div> <div class='deletethumbnail'>X</div>
    </li>
    ...
</ul>

with the photolistitem CSS class defined like this:

.photolistitem
{
    position: relative;
    display: block;
    float: left;    
    list-style-type: none;
    height: 220px;    
    width: 170px;    
    padding: 10px;
    border: solid 1px khaki;
    margin: 12px;
    background: steelblue;
    text-align: center;
}

Note the float:left and the fixed width and height which is a requirement if you want to use the unordered list as a table like display. Items need to be the same size or else the items ends up not aligning properly...

With this layout in place all that needs to happen is to apply the .Sortable() call against the top level <ul> tag and the plug in does the rest, nice UI effects and all.

Saving Sorted Data

Because Sortable is a client side component sort changes are not automatically visible on the server. This means you'll need to somehow let the server know of the sort order update and push the data to the server via an AJAX callback. In the example above I'm using jQuery to reselect all the sorted items (.photolistitem class) and then reading the content from the controls into an array of objects that contains the Id (a hash) and the caption. The array is then sent back to the server via an AJAX callback.

Here's what the JavaScript code for the save operation looks like:

function SavePhotos()
{
    var items = $(".photolistitem");
    var photos = [];
 
    for(var x=0; x<items.length; x++)
    {
        var photo = {}
        photo.id = items[x].id;                
        photo.notes = textFromHtml( $(items[x]).find("div[id$=Notes]").html(),true);                
        photos.push(photo);
    }
 
    var photoList = {};
    photoList.Photos = photos;
    photoList.Title = $("#lblTitle").text();    
    photoList.Description = textFromHtml( $("#lblDescription").html(),true);
 
    // *** Page JSON wrapper    
    httpJson("SaveList",photoList,
            function(result) { showMessage("Changes have been saved...",msgTimeout); },
            pageError);
 
    return photos;
}

On the server side a CallbackMethod (part of West Wind Ajax Toolkit, but you can point this at WCF REST or ASMX Ajax service) the data gets picked up like this:

[CallbackMethod]
public string SaveList(PhotoList photoList)
{
    // *** Write out sort order in increments of 10
    // *** Highest sort order goes to the top
    int sortCount = 10 * this.Album.Photos.Count;
 
    Album.AlbumName = photoList.Title.Trim();
    Album.AlbumDescription = photoList.Description.Trim();
 
    foreach (PhotoListItem changedPhoto in photoList.Photos)
    {
        Photo photo = Album.Photos.GetPhotoByHashCode(changedPhoto.Id);
        if (photo == null)
            continue;
 
        photo.Notes = changedPhoto.Notes.Trim(' ','\r','\n');
        photo.Updated = DateTime.Now;
        photo.SortOrder = sortCount;
 
        sortCount -= 10;
    }
 
    // *** Re-sort the list to update the actual object layout
    this.Album.Sort();
 
    // *** Save the album to disk 
    this.Album.SaveAlbum(this.ConfigFile);
 
    return "Ok";
}

The process is pretty straight forward. If your lists are large and push back lots of data you'd probably also implement some sort of IsDirty flag that determines whether an item has changed so only those items changed are sent to the server. However for sorting you definitely have to send all the items/ids so the server can properly reassemble the items and sort accordingly. It isn't automatic, but it ain't rocket science either.

jQuery UI - Wait for Version 1.5 or use the 1.5 Beta 2 now

When jQuery.ui 1.0 was first released I was pretty excited to see that there'd be a somewhat uniform UI library built ontop of jQuery. Unfortunately Version 1.0 was a really bad release with many of the components not even working out of the box. There were lots of issues with rendering and most of the components worked haphazardly with no consistency between the various control APIs. Most of the controls are based on third party plug-ins that have been drafted into the jQuery.ui API and in version 1.0 that really showed by way of the differing API interfaces.

Version 1.5 - which is not released yet, but available in beta form - fixes these issues with a complete overhaul of the jQuery.ui API. I've used quite a few of the 1.5b components and had no major problems. Many of the controls also have had a big face lift with much nicer UI and effects applied. Using the beta however requires that you also use an interim version of jQuery (1.2.4a). Prior to this release I'd been pulling jQuery out of the SVN repository, patching it together from the base source files, but with the beta 2 release there's now a synched version of jQuery included. If you want to use the beta you need to use this version or a newer one out of the SVN repository.

The current release of jQuery.ui and jQuery work well, but if you're squeamish about beta releases you might want to wait a bit for release.

Online Sample:

http://www.west-wind.com/rick/photoalbum/demoMaui2006/Default.aspx

Click on the Configuration link for the admin portion that includes the sortable code and component.



Customized Loading... Images



Just ran into a cool site that provides a variety of images that show busy status, which is more and more common for Ajax applications. The app lives here:

 http://www.ajaxload.info/

This isn't the first site that collects these various Loading... style images, but what nice about this one is that you can dynamically build the images by specifying colors and background colors and transparency which means you can create images that look good on any kind of background without color bleeding. It looks like this tool rebuilds the images entirely so transparent images look clean no matter what content you stick it ontop of.

Very cool idea. I've already used a few of these to retrofit existing animated gifs and ended up with smaller gifs to boot.

Bookmarked!



Variable Scoping in Anonymous Delegates in C#



Every once in a while when I write code that deals with Anonymous Delegates, I still kinda freak out when it comes to the behavior of closures and the variable scoping that goes along with it. For example, the following code uses a List<T>.Find() Predicate to search for items in the list and requires that a dynamic value is compared to:

public void AddScript(ScriptItem script)
{
    ScriptItem match = null;
 
    // *** Grab just the path
    if (!string.IsNullOrEmpty(script.Src))
    {
        script.FileId = Path.GetFileName(script.Src).ToLower();
 
        match = this.InternalScripts.Find(
            delegate(ScriptItem item)
            {
               ScriptRenderModes mode = this.RenderMode;  // demonstrate this pointer
               return (item.FileId == script.FileId);
            });
    }
 
    if (match == null)                
        this.InternalScripts.Add(script);
    else
        match = script;
} 

The Predicate<T> signature requires a boolean return value and an input parameter of any type (the <T>). The input parameter will be the item iterated over and is of the same time as the list. But the question then becomes: How do you compare that object against a dynamic value?

The freaky thing is the script variable in the AddScript function. It's passed in as a parameter to the outer function so it's effectively a local variable, but yet it is fully visible in the anonymous delegate's own private body. The delegate is in effect just another function, but what's different here is that the anonymous delegate inherits the variable scope of the containing method that is calling it.

To contrast if I were to call an explicit method to handle the Find filter:

match = this.InternalScripts.Find(Exists(script2));

and then create a method that matches this signature I can't access the script variable so this fails to compile:

bool Exists(ScriptItem script2)
{
    return (script2.FileId == script.FileId);   // FAILS obviously due to scoping
}

because script isn't available.

Behind the scenes the C# compiler creates a dynamic delegate class that includes fields for each of the local variables that need to be in scope, so when script  is referenced in the delegate's body it's really referencing the equivalent of this.script. The compiler fixes up the code so that the script property is set when before the method call is made so the delegate code 'appears' to be referencing a variable. If the this pointer is referenced in the delegate code, the compiler also creates a field that holds a reference to the calling class and then fixes up any calls to this to this member instead.

Here's what the compiler generated class looks like:

[CompilerGenerated]
private sealed class <>c__DisplayClass2
{
    // Fields
    public wwScriptContainer <>4__this;
    public ScriptItem script;
 
    // Methods
    public <>c__DisplayClass2();
    public bool <AddScript>b__0(ScriptItem item);
}

and the actual delegate method on the class:

public bool <AddScript>b__0(ScriptItem item)
{
    ScriptRenderModes mode = this.<>4__this.RenderMode;  
    return (this.script.Src == item.Src);
}

Notice that the this pointer is actually referencing a property that has the parent class assigned to it. It's all compiler sugar as well as Visual Studio's Intellisense that gives you the impression that you are in fact inside of closure method. Incidentally one thing that DOESN'T work is checking the this. pointer in the debugger while you are in the delegate code. This cannot be accessed in the debugger inside of the delegate code which would presumably cause some confusion of whether this should point at the delegate (and reveal the compiler magic) or the calling container's class.

Regardless of sleight of hand, the concept of closures is very cool and highly useful. I use it all the time in JavaScript, but damn, it still feels unnatural to me in C#. There's some debate over whether C# anonymous delegates are true lexical closures (take a look at this post and especially the comments), but for most situations that require variable scoping to be passed down to delegates for all intents and purpose the behavior is like that of a typical closure that inherits the calling context's variable scope.

This concept of anonymous delegates and closure scoping is EXACTLY what makes Lambda Expressions work in C# 3.0. Lambdas are just glorified Anonymous Delegates. In fact, the Find() predicate above can also be expressed as a Lambda expression:

match = this.InternalScripts.Find( item => item.FileId == script.FileId );

It's funny sometimes how you end up using some functionality without really understanding what goes on underneath the covers and one day you're using something completely unrelated (in this case JavaScript closures) that make everything click and fall into place. A little spelunking with Reflector later and you feel a heck of a lot more comfortable with several language features...



Visual Studio's JavaScript Editor Really needs a Function/Class Viewer!



During the last week of talking to quite a few Web developers at DevConnections who are doing JavaScript development and during my jQuery and WCF REST talks, a recurring question kept popping up. Why isn't there some way to get a list of functions in the Visual Studio JavaScript editor like in the other languages?

This is a fairly vital feature of a code editor, especially once you start writing a lot more client centric applications that have a fair bit of callback code that is maintained on the client. In fact, the question came up because I was scrolling rapidly over large amounts of code in several demos - or using trusty old CTRL-F - to jump to a given function in the code. In a demo that's annoying as heck, but it's also a problem during day to day development when you're working with more than a few JavaScript functions in a source .js file; client side code accumulates fast, even if you do little more than handle a few client side callbacks.

C# and VB both have class and member drop downs at the top of the code editor:

CSharpFunctionDropDown

There are also document outlines for the HTML and CSS editors, class editors for C# and VB,  but unfortunately there's nothing along these lines available in the Visual Studio JavaScript editor.

I've begged for this feature for a while and it's always been declined as a low priority issue, which I find surprising because to me at least it's pretty high on the productivity list.

I realize that JavaScript parsing and displaying reliable class information is a pretty difficult process. JavaScript's Function based Closure/Class model makes it pretty difficult to figure out exactly what constitutes a function and what constitutes a class. The same issue also applies to the JavaScript Intellisense in Visual Studio which - although pretty good - also misses quite a few scenarios for finding embedded functions and classes and so often provides incomplete information.

There are alternatives though. I've been using Aptana off and on and it does support function and class outlining:

Aptana

As nice as the class view is in Aptana, it's also not perfect. It too misses things. For example, pointing Aptana at the jQuery library also doesn't capture most of the jQuery wrapped set handling functions. As a developer who lives most of the day in Visual Studio I also find the way that Intellisense and the editor in general behaves is a little foreign and I would much prefer to work in VS than another huge external environment.

Still when I'm working on large libraries like the code above or on complex pages that have more than 10 functions on them I tend to switch to using Aptana, simply because I do a lot of jumping back and forth that is much easier to do in this environment than Visual Studio.

So, am I the only one who doesn't see this as a low priority scenario for JavaScript support in Visual Studio? Seems to me this is a vital feature that is incredibly useful for anything but simple JavaScript development.

What do you think?



jQuery AJAX calls to a WCF REST Service



Since I've posted a few jQuery posts recently I've gotten a bunch of feedback to have more content on using jQuery in Ajax scenarios and showing some examples on how to use jQuery to cut out ASP.NET Ajax. In this post I'll show how you can use jQuery to call a WCF REST service without requiring the ASP.NET AJAX ScriptManager and the client scripts that it loads by default. Note although I haven't tried it recently the same approach should also work with ASMX style services.

WCF 3.5 includes REST functionality and one of the features of the new WCF webHttp binding is to return results in a variety of ways that are URL accessible. WCF has always supported plain URL HTTP access, but it's not been real formal and had somewhat limited functionality as parameters had to be encodable as query string parameters. With the webHttp binding there's now an official WCF protocol geared towards providing ASP.NET AJAX JSON compatibility (using WebScript behavior) as well of a slightly cleaner raw JSON implementation (basic webHttp binding).

You can return XML (default), JSON or raw data from WCF REST services. Regardless of content type, natively WCF always wants to return content in a 'wrapped' format which means that both inbound parameters and outbound results are wrapped into an object.

Let's take a look at the message format for a  REST JSON service method.

[ServiceContract(Name="StockService",Namespace="JsonStockService")]    
public interface IJsonStockService
{
    [OperationContract]          
    [WebInvoke(Method="POST",
               BodyStyle=WebMessageBodyStyle.Wrapped,
               ResponseFormat=WebMessageFormat.Json
    )]
    StockQuote GetStockQuote(string symbol);

..

The input message on the wire looks like this:

{"symbol":"MSFT"}

The response looks like this:

{"GetStockQuoteResult":
        {"Company":"MICROSOFT CP",
        "LastPrice":30.00,
        "LastQuoteTime":
        "\/Date(1208559600000-0700)\/",
        "LastQuoteTimeString":"Apr 18, 4:00PM",
        "NetChange":0.78,
        "OpenPrice":29.99,
        "Symbol":"MSFT"}
}

Notice that in both cases an object is used. For the inbound data all parameters are wrapped into an object and rather than just passing the value, the name of the parameter becomes a property in the JSON object map that gets sent to the server. This is actually quite useful - if you're just sending a raw JSON structure you could only pass a single parameter to the server - and that option is also available via the Web BodyStyle=WebMessageBodyStyle.Bare option on the service method.

The outbound result set is also wrapped into an object which is a lot less useful. This is a hold over from WCF which wraps all responses into a message result object, which usually makes sense in order to support multiple result values (ie. out parameters etc.). In a Web scenario however this doesn't really buy you much. Nevertheless if you want to pass multiple parameters to the server you have to use this wrapped format along with the result value.

Calling with jQuery

If you're using jQuery and you'd like to call a WCF REST service it's actually quite easy either with bare or wrapped messages. Bare messages are easier to work with since they skip the wrapping shown above, but as I mentioned you're limited to a single input parameter. So if your service has any complexity you'll likely want to use wrapped messages.

You can opt to either call services using the ASP.NET Ajax logic (WebScriptService behavior) or using the raw service functionality which is shown above.

To call these methods with jQuery is fairly straight forward in concept - jQuery includes both low level and highlevel methods that can call a URL and return JSON data. The two methods available are $.getJSON() which automatically parses result JSON data and $.ajax(), which is a lower level function that has many options for making remote calls and returning data.

getJSON() is useful for simple scenarios where the server returns JSON, but it doesn't allow you to pass JSON data TO the server. The only way to send data to the server with getJSON is via query string or POST data that is sent as standard POST key/value pairs. In all but the simplest scenarios getJSON() is not all that useful.

The lower level $.ajax method is more flexible, but even so it still lacks the capability to pass JSON data TO the server. So little extra work and some external JSON support is required to create JSON output on the client as well as dealing with Microsoft Ajax's date formatting.

Personally I prefer to use a wrapper method for making JSON calls to the server to encapsulate this functionality. Note although this method seems somewhat lengthy it deals with a few important issues that you need to take care of when calling WCF REST Services:

// *** Service Calling Proxy Class
function serviceProxy(serviceUrl)
{
    var _I = this;
    this.serviceUrl = serviceUrl;
 
    // *** Call a wrapped object
    this.invoke = function(method,data,callback,error,bare)
    {
        // *** Convert input data into JSON - REQUIRES Json2.js
        var json = JSON2.stringify(data); 
 
        // *** The service endpoint URL        
        var url = _I.serviceUrl + method;
 
        $.ajax( { 
                    url: url,
                    data: json,
                    type: "POST",
                    processData: false,
                    contentType: "application/json",
                    timeout: 10000,
                    dataType: "text"// not "json" we'll parse
                    success: 
                    function(res) 
                    {                                    
                        if (!callback) return;
 
                        // *** Use json library so we can fix up MS AJAX dates
                        var result = JSON2.parse(res);
 
                        // *** Bare message IS result
                        if (bare)
                        { callback(result); return; }
 
                        // *** Wrapped message contains top level object node
                        // *** strip it off
                        for(var property in result)
                        {
                            callback( result[property] );
                            break;
                        }                    
                    },
                    error:  function(xhr) {
                        if (!error) return;
                        if (xhr.responseText)
                        {
                            var err = JSON2.parse(xhr.responseText);
                            if (err)
                                error(err); 
                            else    
                                error( { Message: "Unknown server error." })
                        }
                        return;
                    }
                });   
    }
}
// *** Create a static instance
var Proxy = new serviceProxy("JsonStockService.svc/");

WCF services are called by their URL plus the methodname appended in the URL's extra path, so here:

JsonStockService.svc/GetStockQuote

is the URI that determines the service and method that is to be called on it.

The code above uses the core jQuery $.ajax() function which is the 'low level' mechanism for specifying various options. Above I'm telling it to accept raw string input (in JSON format), convert the response from JSON into an object by evaling the result, as well as specifying the content type and timeout. Finally a callback handler and error callback are specified.

Note that I override the success handler here to factor out the wrapped response object so that the value received in the callback handler is really only the result and not the wrapped result object. More on this in a second.

The call for the above StockQuote(symbol) call looks like this (including some app specific code that uses the result data):

var symbol = $("#txtSymbol").val();            
Proxy.invoke("GetStockQuote",{ symbol: symbol },
    function (result)
    {   
        //var result = serviceResponse.GetStockQuoteResult;
 
        $("#StockName").text( result.Company + " (" + result.Symbol + ")" ) ;
        $("#LastPrice").text(result.LastPrice.toFixed(2));
        $("#OpenPrice").text(result.OpenPrice.toFixed(2));
        $("#QuoteTime").text(result.LastQuoteTimeString); 
        $("#NetChange").text(result.NetChange.toFixed(2));   
 
        // *** if hidden make visible
        var sr = $("#divStockQuoteResult:hidden").slideDown("slow");
 
        // *** Also graph it
        var stocks = [];
        stocks.push(result.Symbol);
        var url = GetStockGraphUrl(stocks,result.Company,350,150,2);                
        $("#imgStockQuoteGraph").attr("src",url);
    },
    onPageError);

Parameters are passed in as { parm1: "value1", parm2: 120.00 } etc. - you do have to know the parameter names as parameters are matched by name not position.

The result is returned to the inline callback function in the code above and that code assigns the StockQuote data into the document. Notice that the result returned to the callback function is actually NOT a wrapped object. The top level object has been stripped off  so the wrapper is not there anymore.

If you look at the the ajaxJSON function, you can see that it  looks for the first result property in the actual object that WCF returns and uses IT to call the callback function instead - so it's indirect routing. This saves you from the one line of code commented out above and having to know exactly what that Result message name is ( WCF uses <methodName>Result). Not that one line of code would kill you, but it's definitely cleaner and more portable.

The same approach should also work with ASMX style services BTW which uses the same messaging format.

JSON encoding

Note that the ajaxJSON function requires JSON encoding. jQuery doesn't have any native JSON encoding functionality (which seems a big omission, but was probably done to preserve the small footprint). However there are a number of JSON implementations available. Above I'm using the JSON2.js file from Douglas Crockford to serialize the parameter object map into JSON.

There's another wrinkle though: Date formatting. Take another look at the stock quote returned from WCF:

{"GetStockQuoteResult":
        {"Company":"MICROSOFT CP",
        "LastPrice":30.00,
        "LastQuoteTime":
        "\/Date(1208559600000-0700)\/",
        "LastQuoteTimeString":"Apr 18, 4:00PM",
        "NetChange":0.78,
        "OpenPrice":29.99,
        "Symbol":"MSFT"}
}

There's no JavaScript date literal and Microsoft engineered a custom date format that is essentially a marked up string. The format is a string that's encoded and contains the standard new Date(milliseconds since 1970) value. But the actual type of the date value in JSON is a string. If you use standard JSON converters the value will be returned as a string exactly as you see it above. I've talked about the date issues, and hacking existing JSON implementations before. I've modified Crockford's JSON2.JS to support the Microsoft date format so it properly encodes in and outbound data. You can download the hacked JSON2_MsDates.zip if you're interested. You can look at the code to see the modifications that were required, which essentially amounts to pre filtering parsed data before evaling on the .toJSON end and dropping the Data format that Date.prototype.toJSON() produces and instead creating a string in the required format above when doing object encoding.

Bare Messages

If you want a cleaner message format and you're content with single parameter inputs to functions then the WebMessageBodyStyle.Bare can work for you. Bare gives you a single JSON parameter you can pass that is automatically mapped to the first and only parameter of a method. You can't use Bare with any service methods (other than GET input) that include more than one parameter - the service will throw an exception when you access any method (beware: it's a RUNTIME error!).

Bare messages are easier to work with but they are limited because of the single parameter. You can use a single parameter on the server and make that input a complex type like an array to simulate multiple parameters. Using input objects or arrays can work for this. While this works realize that WCF requires an exact type match so any input 'wrapper' types you create yourself have to be mappable to a .NET type.

My first instinct with WCF's web bindings was always to use Bare, but ultimately the wrapped format provides more flexibility even if it is a little uglier on the wire. For AJAX services wrapped seems to make more sense.

Ideally, I would have preferred even more control - wrapped input messages and bare output messages, but I guess you can't have everything <g>...

Other Input Alternatives

Passing JSON messages is one thing you can do - the other option is to pass raw POST variables, which is something that can be done natively with jQuery without requiring a JSON encoder. Basically jQuery allows you to specify data as an object map, and it can turn the object into regular encoded POST parameters.

[OperationContract]          
[WebInvoke(Method="POST",
           BodyStyle=WebMessageBodyStyle.Bare,
           ResponseFormat=WebMessageFormat.Json
 )]
StockQuote GetStockQuote(string symbol);

You'd also need to mark your class:

[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
public class JsonStockService : StockServiceBase

and enable ASP.NET compatibility in web.config (see my WCF REST Configuration Post for details)

If you prefer the simplified logic and you can use POST input data (which works well if you rather post back to a handler or the same ASPX page) you can get away with the following:

function ajaxJsonPost(method,data,callback,error)
{
    var url = "JsonStockService.svc/" + method;
    $.ajax( { 
                url: url,
                data: data,
                type: "POST",
                processData: true,
                contentType: "application/json",
                timeout: 10000,
                dataType: "json",
                success: callback,
                error: error
            });   
}

When you send data like this you can actually change the message format to Bare and get just a raw object response. jQuery can either except a raw POST string for the data parameter or an object whose properties and values are turned into POST key value pairs.

If you want to use POST behavior with WCF though,  you need to enable ASPNET Compatibility on the REST service - otherwise the HttpContext.Current.Request is not available since WCF REST by default is trying to be host agnostic.  For more information on how to configure WCF REST services check my previous post on WCF REST configuration last week.

This format might be preferrable if you are indeed building a public API that will be externally accessed. Raw POST data interchange is more common for many Ajax libraries, and also lends it self to straight HTTP clients that don't have JSON encoding features built in. For public APIs this makes plenty of sense. Remember that if you care about date formatting you may want to add the explicit JSON2 parsing code into the success callback (I left this out here for simplicities sake).

Error Handling

One more issue you'll want to be very careful of with WCF REST Services when you're using non-WebScriptService (ASP.NET AJAX style) behavior: When an error occurs WCF unfortunately throws an HTML error page rather than a JSON or XML fault message. That's a big problem if you want to return meaningful error messages to your client application - the only way to retrieve the error is by parsing the messy and very bulky HTML document returned.I've tried finding some way to get the REST services to throw a full JSON based error message and I haven't found a way to do this. JSON error messages seem to only work when you're using WebScriptService which is the full ASP.NET AJAX emulation. Under WebScriptService behavior the message returns the standard Exception like structure that includes a .Message and .StackTrace property that lets you echo back errors more easily.

In the end this means that even if you are using a non-MS Ajax client it might be the best solution to use the ASP.NET AJAX style WebHttp binding, simply because it provides the behavior that you most commonly require. There's nothing lost by doing so. You don't incur any client ASP.NET AJAX client requirements, but you do get the wrapped format input and exceptions properly wrapped on errors, plus this format is easier to implement because it doesn't require any special attributes on each individual operation/method as it's a fixed format. On the downside  you do lose the ability to use UrlTemplates which might be useful in some situations, but it's probably not a common scenario that you need this for pure AJAX services.



LINQPad as a Code Snippet Execution Engine



If you haven't checked out LINQPad before it's probably high time. LINQPad is a cool little utility that was mainly created to allow you to test LINQ expressions and see them produce a result and output the results in a nice easy to visualize format. It's great for running LINQ Queries without having to fire up Visual Studio.

LINQPad does a great job at LINQ execution and visualization, but it has a lot more uses than just a LINQ query tool. It's basically a snippet editor that allows you to save snippets and more importantly, execute just about any code that you can write as an expression or single function block . You can execute both Expressions which is a single command that returns a result or a single block of commands or a Statement which is a block of commands in a single execution block (essentially what would amount to a method body).

It's awesome if you just want to very quickly verify how some .NET function or expression  works without having to write a test, console output routine or change your code and run it with the debugger.

For example, just a minute ago I was having some issues with a Path.Combine() in an application where the two path components passed in would be a path and filename, except that the filename could also have a leading slash and it was returning what I thought are unexpected results. Here's what this looks like in LINQ Pad after I needed to do some quick experiments with various different combinations of files and paths:

 LinqPadExecute

You can see the unfortunate result in the first result line in the Results panel which produces \test.tmp instead of the expected combined path. Actually the behavior is correct - the combination of the two paths sees no common path to combine so it just uses the latter part. Still I expected the function to assume I wanted to combine two paths regardless of the leading slash. <shrug>

Anyway, using LINQPad it was a piece of cake to paste the line and execute it without even touching the code I was working on in Visual Studio. LINQPad uses a .Dump() extension method on object to display the content of just about any structure to text output. It'll dump simple values with .ToString() and complex structures in an easy to visual tabular display. For example, above I added an anonymous type to the result which is shown in the table in the results pane above.

The cool thing is that it works with any code. There's even an Advanced option on the Query menu that allows you to import assembly references and namespaces so you can test your own assemblies.

Of course LINQPad - as the name implies - also works with LINQ queries and does a wonderful job of displaying LINQ and LINQ to SQL results:

LinqPadSqlResult

Output can be displayed both as a result table view, the raw SQL (from .ToString()) and a useful code conversion from the LINQ Expression syntax to LINQ command syntax using command chaining of the various LINQ extensions methods.

There's no installation - it's a single self contained EXE you can copy anywhere assuming you have .NET 3.5 installed.

If you haven't looked at LINQPad before - even if you're not using LINQ yet, be sure to check it out...This is one of those useful tools you just should always have around and "linqed" to a hotkey, in VS or as I do with SlickRun. It's a great way to quickly check out many things .NET.



Byte Order Marks and XmlDocument Streaming to HTTP



Argh. I just got bit again by Byte Order marks that get sent out over HTTP when using ASP.NET. Basically the problem is that .NET's default XmlTextWriter encoding uses UTF-8 and the default Encoding includes generation of a BOM as part of the output. If that output gets sent to the Response output the BOM gets sent along with it which is definitely what you want.

In case you don't know what a BOM is - it's the the preamble that gets attached to the beginning of the document to identify its Encoding. There are different preambles for different Encodings. It's meant for files stored on disk so that when a file is opened there's a quick way for an editor to detect the encoding for the file. If you look at a UTF-8 document with a hex editor (or any editor that doesn't apply any encoding) you'd see:

<?xml version="1.0" encoding="utf-8"?>

If you use UTF8Encoding in .NET it defaults to generate this BOM prefix by default. Most XML objects in .NET too use XmlTextWriter for streaming output to, and they too defaults to UTF8Encoding. So if you stream XML to disk you'll get the right result which is what you want.

However, if you're streaming the XML to some other direct output  source such as Http from ASP.NET you definitely don't want the BOM in front - it in fact makes the XML document invalid. I just had some code that does the post the content of an XmlDocument to an Http server. The following code incorrectly streams  and ends up sending a BOM to the server:

public string PostDocument(string url, XmlDocument doc)
    {
 
        // *** Output from Http request will be stored here and returned
        string result = null;
 
        MemoryStream ms = new MemoryStream(1024);
 
           XmlTextWriter writer = new XmlTextWriter(ms);
        
            doc.Save(ms);
 
            // *** Rewind the stream
            ms.Position = 0;
 
            // *** Http Wrapper Component            
            wwHttp http = new wwHttp();
 
            // *** Pre-create request object so we can set properties on it
            http.CreateWebRequestObject(url);
 
            // *** Content will be XML
            http.ContentType = "text/xml; charset=utf-8";
 
            // *** Pick up the client Http headers that we need to add to the request
            Dictionary<string, string> headers = GetCreditDecisionHttpHeaders(doc);
 
            // *** Add all Http headers to the request
            foreach (KeyValuePair<string, string> kv in headers)
            {
                http.WebRequest.Headers.Add(kv.Key, kv.Value);
            }
 
            // *** apply the POST data from stream
            http.SetPostStream(ms);
 
            // *** And send the request
            result = http.GetUrl(url);
 
        
     &nbs