Brian Mains

Catch me on linked in at: http://linkedin.com/in/brianmains, or follow me on twitter at: @brianmains.

October 2009 - Posts

Nucleo Link Control Overview

My latest release at http://www.codeplex/nucleo also features a new Link control (in the Nucleo.Web.Controls namespace).  This control tries to integrate two kinds of links; clickable links which fire an event, and redirection links that navigate to another site.  The link control incorporates an enumeration to incorporate this: the ClickAction property of type LinkClickAction.  When set to FIreEvent, the client-side clicked event or server-side clicked event (depending on rendering mode set by the RenderMode property) of the control, whereas Redirect fires a Redirecting event.

The redirecting parameters can be set by establishing the NavigateUrl property.  This property specifies the location to redirect to.  Another option, Target, specifies whether to use a new window to open the link in, or the same window.  The link also specifies a NavigateUrlFormatString that you can use to do something like this:

<n:Link ... NavigateUrl='<%# Eval("Key") %>' NavigateUrlFormatString="products.aspx?id={0}" />

When a format string is specified, the navigateurl property is injected in the format string, as a convenience option.  Only one format placeholder is available.  The server component also has helper methods to get the final values for text (which has Text and TextFormat properties), navigate url, and more.  The GetText, GetNavigateUrl, and GetTarget methods are convenience methods for extracting this information as the control would need for rendering.

These options can be changed on the client-side; each of the main properties (navigateUrl, clickAction, target, text, etc.) is available on the client except for the format strings.  So you can change the way the link reacts to clicks, change where it navigates to, and more.

var link = $find("<%= l1.ClientID %>");
link.set_text("New Text");
link.set_clickAction(Nucleo.Web.Controls.LinkClickAction.Redirect);
link.set_navigateUrl("http://www.yahoo.com");
link.refreshUI();

Note the refreshUI method; this is a method that's used to perform the actual updates.  This is important because the UI changes won't occur until that method calls.  The reason is because I created a batch method to perform these updates for performance reasons (updating on every setter would be cumbersome).

Posted: Sat, Oct 31 2009 13:53 by bmains | with no comments
Filed under: ,
Accessing Service Oriented API's using an IService Interface

If you've used MVC, you know the System.Web.Abstractions API offers you a lot of capabilities to make it easy to write unit tests in your MVC controllers.  It's really easy to setup a Moq or TypeMock unit test to create a fake implementation of objects like HttpContextBase.  Some objects are not as testable.  For instance, UrlHelper may not be as easy to implement testing with (although TypeMock can test pretty much any object very easily since it doesn't require a DI setup or interfaces).  Rather than leverage this approach, I chose an approach not just limited to web forms, and something that may be available in a windows, silverlight, or WPF environment as well.  Welcome the ApplicationContext object and the IService interface.

ApplicationContext is a central object that is used to make services available to those who need it.  You have to go through a process of loading these services; however, this process isn't that hard (will cover in another blog post).  To use the application context looks something like:

ApplicationContext context = ApplicationContext.GetCurrent();
ILoggerService service = context.GetService<ILoggerService>();

Every service that the application context uses implements IService (this interface doesn't really do anything, but simply is used as a marker).  ILoggerService happens to be one of the services available (ILoggerService implements IService) and so it's retrievable vai the ApplicationContext object.  Built into the framework is the NucleoContext namespace (which contains environment-agnostic services) and Nucleo.Web.Context (web/MVC specific services) that you can use the ApplicationContext object to retrieve.

The idea of this object is to make available core services.  For instance, in MVC, you can instantiate the service you need (HttpContextWrapper, HttpRequestWrapper, etc.).  Instead of using this, you can use the application context to request these services instead.  I don't have all of the existing web services created; however, I do have services available for cookies, querystring, forms, and more.  Rather than create one big request object, I instead break up each of these into smaller services by function.

How do you retrieve?  That's the purpose of the service loader, a subject we'll discuss next.  You can get the latest code base for this example from: http://www.codeplex.com/nucleo

Posted: Fri, Oct 30 2009 22:09 by bmains | with 1 comment(s)
Filed under: ,
Using the Nucleo Button

I've been working on a project available at for http://www.codeplex.com/nucleo.  It's a project I've had in the works for a while, and it's finally coming to fruition.  So I am starting to create blog posts explaining features about these controls.  I am really excited about this button because I think it offers you more than what other control vendors offer you (at least the ones I seen, because I don't know every control suite out there).  Anyway, my button comes with some nice features.

First, it has a DisableUntilPageLoad property that will disable the button until page load scripts have run.  This is a useful feature I found in Professional ASP.NET AJAX from Wrox that really does make sense.  So I added it into my button control, which simply can be enabled via:

<n:Button ... DisableUntilPageLoad="True" />

And now the button doesn't enable until page loads on the client.  Note: It's up to you to ensure JavaScript works :-;  Next, we have the ability to disable the button when it clicks by setting the DisableOnFirstClick property to true.  This disables the button permanently, but can be re-enabled using the enabled client-side property.  The DisableOnFirstClickTimeout specifies a timeout in seconds, which will be used to re-enable a button.  This is a nice feature because often developers want to prevent double-clicks from happening, yet still ensure that they can click the button.  Using these setting:

<n:Button DisableOnFirstClick="True" DisableOnFirstClickTimeout="300" />

This disables the button on click, then re-enables it at 300 milliseconds.  The button does support all the traditional IButtonControl implementations, but doesn't use the ASP.NET implementation; rather, I use a cleaner approach that can be used on both the server and the client.

The button also specifies a mode to render in, whether link button, push button, or image button.  This mode is then rendered appropriately.  This then requires only one button instance, and can be changed on the server.  It currently cannot be changed on the client, but should be something I implement in the future.

This are some of the Button control's available offerings.  More to come soon on some of the other controls.

 

Posted: Tue, Oct 27 2009 21:26 by bmains | with no comments
Filed under: ,
Pro Asp.NET MVC Framework (Apress) by Steve Sanderson

Rating: 5 out of 5

I believe Pro ASP.NET MVC Framework is one of the best books on the market about MVC.  This book is crammed with a lot of information that you need to know as a developer.  While he doesn't cover each subject fully (no book really does that), he does cover the major topic points related to MVC in-depth, and touches upon the other concerts that you need to be aware of to implement or customize MVC for your own purposes.  I’ve broken up my review into several major subsections related to the book and analyze each one individually.  From an overall level, I think the book really did well in its explanation and examples of MVC.

Book's Knowledge

This book is really crammed with lots of valuable information.  I find myself referring back to the book when working with MVC, because it has a lot of various important sections about how to use JQuery to dynamically change MVC partial views within a view, how to customize the creation of a controller, and other important facts.  There is so many small or medium details regarding the MVC framework that is important to know about covered in this book, that it does really make it a very beneficial book.

The chapters on each major feature (views, routing, controllers, etc.) are very long, which is great because they contain so much information about each of the subjects.  I was really impressed with the information packed into each of these chapters.  After reading the book, I felt comfortable enough to work on MVC and understand some of the concerns when implementing MVC for my own applications.  I felt there was minimal downtime trying to play with MVC to understand its inner-workings; I really felt confortable jumping in.

Writing Style

I really like Steven's ability to clearly articulate points about MVC.  If the writer is not fluent, I tend to lose interest, but I didn't lose interest at all in this book.  This book doesn't just talk about the functionality, but actually illustrates its use through examples and theory, which is important for such a big subject.  That's not to say he doesn't explain his code, which he does in the right amount of detail.

Content Structure

Though a pro book, the author ensures that he covers the basic prerequisites for the book, to fill in the user how MVC works.  The book continues on with three chapters of a sample MVC application, explaining it some as he goes, following up with most of the book detailing each features. 

The main complaint of the book that I have is that Chapters 4, 5, and 6 cover the basics of creating an MVC sports store application and tries to get you familiar with MVC by jumping right in without a lot of preliminary discussion.  While he does discuss what he’s illustrating, I feel it would have been helpful to cover the documentation of the features first, and then rolled through the example last, with a bigger/more complex example.

The plus to this design is that the sample walks you through the basics, and the subsequent materials enhance your understanding of routing, views, controllers and actions, data entry and model binding, AJAX and client-scripting, and security.

I found much use alone out of the chapters on using AJAX to use an unobtrusive JavaScript approach and the concerns to have with implementing security (since ASP.NET web forms handled certain security features for you automatically and MVC does not).

 
Implementation
 
While I do have a deep technical background, the concept of MVC is somewhat foreign to me; I had a familiarity to the pattern, but didn't know anything about the product.  After reading this book, I felt very confident about my ability to create an MVC site.  There were some curveballs and I had to reference the book again and again, but I felt overall that this book was a fantastic resource to get me going.  It's the only book I read on the subject (outside of the NerdDinner resource provided by Scott Guthrie).

Conclusion

MVC is a great product.  While in its infancy (2.0 has some great features coming), MVC gives you control over the UI that web forms took away.  MVC is a big undertaking and does require some knowledge about how it works.  I believe this book is a great way to take a big chunk out of the mystery of MVC, especially for those coming from a web forms world.

Posted: Mon, Oct 19 2009 21:08 by bmains | with no comments
Filed under:
ADO.NET Entity Model Helpers

I'm starting to get into a project using ADO.NET entity model.  This is a pretty cool technology, and I like a lot of the features (especially the logical model approach).  There are some things I really dislike about Phase 1, like having to delete the entire model or edit SSDL manually (or with XML tool) - anybody know of some free tools available for this?  But overall, I like the approach, and the concept, so I look forward to adding features.

Some features I want to add is automatic logging.  Sometimes, you just need to know what's going on with your application to see if the logic is working correctly.  I often create a logger class, create an ILogger interface with a LogError and LogMessage methods, and create derived classes to log to event log, console, health monitoring, etc.  That is out of scope for this article, but I want to focus on the idea of extensibility.  I've been reading articles about how to plugin to the provider architecture and other approaches, but I don't personally want to affect the architecture.  Rather, I'd rather take the wrapping approach.  This is separated and isolated from any provider architecture changes over the years.  While that's not a major concern anyway (at least for me), a separate class seems like a good approach.

So I use a class that does something like this:

public class ObjectContextHelpers
{
    public static void SaveNewObject(CustomObjectContext context, string entitySetName, object entity)
    {
         //get a reference to the logger - pass in as ref or via singleton, or some other approach
        logger.LogMessage("Attempting to save object for entity set " + entitySetName);
        //Can log other details, number of objects commiting, details about object state entries, and other information

        try
        {
            context.AddObject(entitySetName, entity);

        }
        catch(Exception ex) { logger.LogMessage("Saving object failed: " + ex.ToString()); }
  
        logger.LogMessage("Saved object for entity set " + entitySetName);
    }

    public static CustomObjectContext Create()
    {
         return new CustomObjectContext(ConfigurationManager.ConnectionStrings["ConnString"].ConnectionString);
    }
}

Here we have a Create method that uses one common connection string, which is a connection string pre-configured (assuming that you aren't building a custom library that may require configurability).

Posted: Thu, Oct 1 2009 20:17 by bmains | with no comments
Filed under: