BusinessRx Community

Dedicated to the advancement of software, technology and the people who devote their lives to it.

Welcome to BusinessRx Community Sign in | Join | Help
in Search

BusinessRx Reading List

These blog entries are written by industry experts and leaders. We consider this content to be a good read for any software developer or web technologist.

Browse by Tags

All Tags » MVC   (RSS)

  • ASP.NET MVC 2 (Release Candidate 2) Now Available

    [In addition to blogging, I am also now using Twitter for quick updates and to share links. Follow me at: twitter.com/scottgu]

    Earlier this evening the ASP.NET team shipped ASP.NET MVC (Release Candidate 2) for VS 2008/.NET 3.5.  You can download it here.

    The RC2 release of ASP.NET MVC 2 is a follow-up to the first ASP.NET MVC 2 RC build that we shipped in December.  It includes a bunch of bug fixes, performance work, and some final API and behavior additions/changes.  Below are a few of the changes between the RC1 and RC2 release (read the release notes for even more details):

    • The new ASP.NET MVC 2 validation feature now performs model-validation instead of input-validation (this means that when you use model binding all model properties are validated instead of just validations on changed values of a model).  This behavior change was based on extensive feedback from the community.
    • The new strongly-typed HTML input helpers now support lambda expressions which reference array or collection indexes.  This means you can now write code like Html.EditorFor(m=>m.OrdersIdea) and have it correctly output an HTML <input> element whose “name” attribute contains the index (e.g. Orders[0] for the first element), and whose “value” contains the appropriate value.
    • The new templated Html.EditorFor() and Html.DisplayFor() helper methods now auto-scaffold simple properties (and do not render complex sub-properties by default).  This makes it easier to generate automatic scaffolded forms.  I’ll be covering this support in a future blog post.
    • The “id” attribute of client-script validation message elements is now cleaner.  With RC1 they had a form0_ prefix.  Now the id value is simply the input form element name postfixed with a validationMessage string (e.g. unitPrice_validationMessage).
    • The Html.ValidationSummary() helper method now takes an optional boolean parameter which enables you to control whether only model-level validation messages are rendered by it, or whether property level validation messages are rendered as well.  This provides you with more UI customization options for how validation messages are displayed within your UI.
    • The AccountController class created with the default ASP.NET MVC Web Application project template is cleaner.
    • Visual Studio now includes scaffolding support for Delete action methods within Controllers, as well as Delete views (I always found it odd that the default T4 templates didn’t support this before).
    • jQuery 1.4.1 is now included by default with new ASP.NET MVC 2 projects, along with a –vsdoc file that provides Visual Studio documentation intellisense for it.
    • The RC2 release has some significant performance tuning improvements (for example: the lambda based strongly-typed HTML helpers are now much faster).

    Today’s RC2 release only work with VS 2008 and .NET 3.5.  We’ll shortly be releasing the VS 2010 RC (which will be available for everyone to download). It will include ASP. NET MVC 2 support built-in (no separate download required).

    Hope this helps,

    Scott

    P.S. The source code for the ASP.NET MVC RC2 release (along with a MVC futures library that goes with it) can be downloaded here. You can learn even more about ASP.NET MVC 2 by reading the ASP.NET MVC 2 blog series I’m working on.

  • About Technical Debates (and ASP.NET Web Forms and ASP.NET MVC debates in particular)

    [In addition to blogging, I am also now using Twitter for quick updates and to share links. Follow me at: twitter.com/scottgu]

    Technical debates are discussed endlessly within the blog-o-sphere/twitter-verse, and they range across every developer community. Each language, framework, tool, and platform inevitably has at least a few going on at any particular point in time.

    Below are a few observations I’ve made over the years about technical debates in general, as well as some comments about some of the recent discussions I’ve seen recently about the topic of ASP.NET Web Forms and ASP.NET MVC in particular.

    General Observations About Technical Debates

    Below are a few general observations independent of any specific technical debate:

    a) Developers love to passionately debate and compare languages, frameworks, APIs, and tools.  This is true in every programming community (.NET, Java, PHP, C++, Ruby, Python, etc).  I think you can view these types of religious technical debates in two ways:

    1. They are sometimes annoying and often a waste of time.
    2. They are often a sign of a healthy and active community (since passion means people care deeply on both sides of a debate, and is far better than apathy).

    Personally I think both points are true.

    b) There is never only “one right way” to develop something. As an opening interview question I sometimes ask people to sort an array of numbers in the most efficient way they can.  Most people don’t do well with it.  This is usually not because they don’t know sort algorithms, but rather because they never think to ask the scenarios and requirements behind it – which is critical to understanding the most efficient way to do it.  How big is the sequence of numbers? How random is the typical number sequence (is it sometimes already mostly sorted, how big is the spread of numbers, are the numbers all unique, do duplicates cluster together)? How parallel is the computer architecture?  Can you allocate memory as part of the sort or must it be constant?  Etc. These are important questions to ask because the most efficient and optimal way to sort an array of numbers depends on understanding the answers. 

    Whenever people assert that there is only “one right way” to a programming problem they are almost always assuming a fixed set of requirements/scenarios/inputs – which is rarely optimal for every scenario or every developer.  And to state the obvious - most problems in programming are far more complex than sorting an array of numbers.

    c) Great developers using bad tools/frameworks can make great apps. Bad developers using great tools/frameworks can make bad apps. Be very careful about making broad assumptions (good or bad) about the quality of the app you are building based on the tools/frameworks used.

    d) Developers (good and bad) can grow stronger by stretching themselves and learning new ideas and approaches.  Even if they ultimately don’t use something new directly, the act of learning it can sharpen them in positive ways.

    e) Change is constant in the technology industry.  Change can be scary.  Whether you get overwhelmed by change, though, ultimately comes down to whether you let yourself be overwhelmed.  Don’t stress about having to stop and suddenly learn a bunch of new things - rarely do you have to. The best approach to avoid being overwhelmed is to be pragmatic, stay reasonably informed about a broad set of things at a high-level (not just technologies and tools but also methodologies), and have the confidence to know that if it is important to learn a new technology, then your existing development skills will mostly transition and help.  Syntax and APIs are rarely the most important thing anyway when it comes to development – problem solving, customer empathy/engagement, and the ability to stay focused and disciplined on a project are much more valuable.

    f) Some guidance I occasionally give people on my team when working and communicating with others:

    1. You will rarely win a debate with someone by telling them that they are stupid - no matter how well intentioned or eloquent your explanation of their IQ problems might be.
    2. There will always be someone somewhere in the world who is smarter than you - don’t always assume that they aren’t in the room with you.
    3. People you interact with too often forget the praise you give them, and too often remember a past insult -  so be judicious in handing them out as they come back to haunt you later. 
    4. People can and do change their minds - be open to being persuaded in a debate, and neither gloat nor hold it against someone else if they also change their minds.

    g) I always find it somewhat ironic when I hear people complain about programming abstractions not being good.  Especially when these complaints are published via blogs – whose content is displayed using HTML, is styled with CSS, made interactive with JavaScript, transported over the wire using HTTP, and implemented on the server with apps written in higher-level languages, using object oriented garbage collected frameworks, running on top of either interpreted or JIT-compiled byte code runtimes, and which ultimately store the blog content and comments in relational databases ultimately accessed via SQL query strings.  All of this running within a VM on a hosted server – with the OS within the VM partitioning memory across kernel and user mode process boundaries, scheduling work using threads, raising device events using signals, and using an abstract storage API fo disk persistence.  It is worth keeping all of that in mind the next time you are reading a “ORM vs Stored Procedures” or “server controls – good/bad?” post.  The more interesting debates are about what the best abstractions are for a particular problem.

    h) The history of programming debates is one long infinite loop – with most programming ideas having been solved multiple times before.  And for what it’s worth – many of the problems we debate today were long ago solved with LISP and Smalltalk.  Ironically, despite pioneering a number of things quite elegantly, these two languages tend not be used much anymore. Go figure.

    Some Comments Specific to ASP.NET Web Forms / ASP.NET MVC debates:

    Below are a few comments specific to some of the recent debates that I’ve seen going around within the community as to whether a ASP.NET Web Forms or ASP.NET MVC based approach is best:

    a) Web Forms and MVC are two approaches for building ASP.NET apps. They are both good choices. Each can be the “best choice” for a particular solution depending on the requirements of the application and the background of the team members involved. You can build great apps with either.  You can build bad apps with either. You are not a good or bad developer depending on what you choose. You can be absolutely great or worthless using both.

    b) The ASP.NET and Visual Studio teams are investing heavily in both Web Forms and MVC.  Neither is going away.  Both have major releases coming in the months ahead.  ASP.NET 4 includes major updates to Web Forms (clean ClientIDs and CSS based markup output, smaller ViewState, URL Routing, new data and charting controls, new dynamic data features, new SEO APIs, new VS designer and project improvements, etc, etc).  ASP.NET 4 will also ship with ASP.NET MVC 2 which also includes major updates (strongly typed helpers, model validation, areas, better scaffolding, Async support, more helper APIs, etc, etc).  Don’t angst about either being a dead-end or something you have to change to.  I suspect that long after we are all dead and gone there will be servers somewhere on the Internet still running both ASP.NET Web Forms and ASP.NET MVC based apps.

    c) Web Forms and MVC share far more code/infrastructure/APIs than anyone on either side of any debate about them ever mentions - Authentication, Authorization, Membership, Roles, URL Routing, Caching, Session State, Profiles, Configuration, Compilation, .aspx pages, .master files, .ascx files, Global.asax, Request/Response/Cookie APIs, Health Monitoring, Process Model, Tracing, Deployment, AJAX, etc, etc, etc.  All of that common stuff you learn is equally valid regardless of how you construct your UI.  Going forward we’ll continue to invest heavily in building core ASP.NET features that work for both Web Forms and MVC (like the URL Routing, Deployment, Output Caching, and DataAnnotations for Validation features we are adding with ASP.NET 4). 

    d) I often find debates around programming model appropriateness and abstractions a little silly. Both Web Forms and MVC are programming web framework abstractions, built on top of a broader framework abstraction, programmed with higher level programming languages, running on top of a execution engine abstraction that itself is running on top of a giant abstraction called an OS.  What you are creating with each is HTML/CSS/JavaScript (all abstractions persisted as text, transmitted over HTTP – another higher level protocol abstraction). 

    The interesting question to debate is not whether abstractions are good or not – but rather which abstractions feels most natural to you, and which map best to the requirements/scenarios/developers of your project.

    e) We are about to do a pretty major update to the www.asp.net site.  As part of that we will be posting more end to end tutorials/content (for both Web Forms and MVC).  We will also be providing tutorials and guidance that will help developers quickly evaluate both the Web Forms and MVC approach, easily learn the basics about how both work, and quickly determine which one feels best for them to use. This will make it easy for developers new to ASP.NET, as well as developers who already know either Web Forms or MVC, to understand and evaluate the two approaches and decide which they want to use.

    f) Decide on a project about whether you want to use Web Forms or MVC and feel good about it.  Both can be good choices.  Respect the choices other people make – the choice they have made is also hopefully a good one that works well for them.  Keep in mind that in all likelihood they know a lot more about their own business/skills than you do.  Likewise you hopefully know a lot more about your own business/skills than they do.

    g) Share ideas and best practices with others.  That is a big part of what blogs, forums, listservs and community is all about.  What makes them work great is when people know that their ideas aren’t going to be ripped to shreds, and that they will be treated with respect.  Be constructive, not snarky. Teach, don’t lecture. Remember there is always someone else out there who you can also learn from.

    Hope this helps,

    Scott

  • ASP.NET MVC 2: Model Validation

    [In addition to blogging, I am also now using Twitter for quick updates and to share links. Follow me at: twitter.com/scottgu]

    This is the second in a series of blog posts I’m doing on the upcoming ASP.NET MVC 2 release.  This blog post covers some of the validation improvements coming with ASP.NET MVC 2.

    ASP.NET MVC 2 Validation

    Validating user-input and enforcing business rules/logic is a core requirement of most web applications.  ASP.NET MVC 2 includes a bunch of new features that make validating user input and enforcing validation logic on models/viewmodels significantly easier.  These features are designed so that the validation logic is always enforced on the server, and can optionally also be enforced on the client via JavaScript.  The validation infrastructure and features in ASP.NET MVC 2 are designed so that:

    1) Developers can easily take advantage of the DataAnnotation validation support built-into the .NET Framework.  DataAnnotations provide a really easy way to declaratively add validation rules to objects and properties with minimal code.   

    2) Developers can optionally integrate either their own validation engine, or take advantage of existing validation frameworks like Castle Validator or the EntLib Validation Library. ASP.NET MVC 2’s validation features are designed to make it easy to plug-in any type of validation architecture – while still taking advantage of the new ASP.NET MVC 2 validation infrastructure (including client-side validation, model binding validation, etc).

    This means that enabling validation is really easy for common application scenarios, while at the same time still remaining very flexible for more advanced ones.

    Enabling Validation with ASP.NET MVC 2 and DataAnnotations

    Let’s walkthrough a simple CRUD scenario with ASP.NET MVC 2 that takes advantage of the new built-in DataAnnotation validation support.  Specifically, let’s implement a “Create” form that enables a user to enter friend data:

    image

    We want to ensure that the information entered is valid before saving it in a database – and display appropriate error messages if it isn’t:

    image

    We want to enable this validation to occur on both the server and on the client (via JavaScript).  We also want to ensure that our code maintains the DRY principle (“don’t repeat yourself”) – meaning that we should only apply the validation rules in one place, and then have all our controllers, actions and views honor it.

    Below I’m going to be using VS 2010 to implement the above scenario using ASP.NET MVC 2.  You could also implement the exact same scenario using VS 2008 and ASP.NET MVC 2 as well.

    Step 1: Implementing a FriendsController (with no validation to begin with)

    We’ll begin by adding a simple “Person” class to a new ASP.NET MVC 2 project that looks like below:

    image

    It has four properties (implemented using C#’s automatic property support, which VB in VS 2010 now supports too – woot!).

    We’ll then add a “FriendsController” controller class to our project that exposes two “Create” action methods.  The first action method is called when an HTTP-GET request comes for the /Friends/Create URL.  It will display a blank form for entering person data.  The second action method is called when an HTTP-POST request comes for the /Friends/Create URL.  It maps the posted form input to a Person object, verifies that no binding errors occurred, and if it is valid will eventually save it to a database (we’ll implement the DB work later in this tutorial).  If the posted form input is invalid, the action method redisplays the form with errors:

    image

    After we’ve implemented our controller, we can right-click within one of its action methods and choose the “Add View” command within Visual Studio – which will bring up the “Add View” dialog.  We’ll choose to scaffold a “Create” view that is passed a Person object:

    image

    Visual Studio will then generate a scaffolded Create.aspx view file for us under the \Views\Friends\ directory of our project.  Notice below how it takes advantage of the new strongly-typed HTML helpers in ASP.NET MVC 2 (enabling better intellisense and compile time checking support):

    image

    And now when we run the application and hit the /Friends/Create URL we’ll get a blank form that we can enter data into:

    image

    Because we have not implemented any validation within the application, though, nothing prevents us from entering bogus input within the form and posting it to the server.

    Step 2: Enabling Validation using DataAnnotations

    Let’s now update our application to enforce some basic input validation rules.  We’ll implement these rules on our Person model object – and not within our Controller or our View.  The benefit of implementing the rules within our Person object is that this will ensure that the validation will be enforced via any scenario within our application that uses the Person object (for example: if we later added an edit scenario).  This will help ensure that we keep our code DRY and avoid repeating rules in multiple places.

    ASP.NET MVC 2 enables developers to easily add declarative validation attributes to model or viewmodel classes, and then have those validation rules automatically be enforced whenever ASP.NET MVC performs model binding operations within an application.  To see this in action, let’s update our Person class to have a few validation attributes on it.  To do this we’ll add a “using” statement for the “System.ComponentModel.DataAnnotations” namespace to the top of the file – and then decorate the Person properties with [Required], [StringLength], [Range], and [RegularExpression] validation attributes (which are all implemented within that namespace):

    image

    Note: Above we are explicitly specifying error messages as strings. Alternatively you can define them within resource files and optionally localize them depending on the language/culture of the incoming user.  You can learn more about how to localize validation error messages here.

    Now that we’ve added the validation attributes to our Person class, let’s re-run our application and see what happens when we enter bogus values and post them back to the server:

    image

    Notice above how our application now has a decent error experience.  The text elements with the invalid input are highlighted in red, and the validation error messages we specified are displayed to the end user about them.  The form is also preserving the input data the user originally entered – so that they don't have to refill anything.  How though, you might ask, did this happen? 

    To understand this behavior, let’s look at the Create action method that handles the POST scenario for our form:

    image

    When our HTML form is posted back to the server, the above method will be called.  Because the action method accepts a “Person” object as a parameter, ASP.NET MVC will create a Person object and automatically map the incoming form input values to it.  As part of this process, it will also check to see whether the DataAnnotation validation attributes for the Person object are valid.  If everything is valid, then the ModelState.IsValid check within our code will return true – in which case we will (eventually) save the Person to a database and then redirect back to the home-page. 

    If there are any validation errors on the Person object, though, our action method redisplays the form with the invalid Person.  This is done via the last line of code in the code snippet above.

    The error messages are then displayed within our view because our Create form has <%= Html.ValidationMessageFor() %> helper method calls next to each <%= Html.TextBoxFor() %> helper.  The Html.ValidationMessageFor() helper will output the appropriate error message for any invalid model property passed to the view:

    image

    The nice thing about this pattern/approach is that it is pretty easy to setup – and it then allows us to easily add or change validation rules on our Person class without having to change any code within our controllers or views.  This ability to specify the validation rules one place and have it be honored and respected everywhere allows us to rapidly evolve our application and rules with a minimum amount of effort and keep our code very DRY.

    Step 3: Enabling Client-side Validation

    Our application currently only performs server-side validation – which means that our end users will need to perform a form submit to the server before they’ll see any validation error messages.

    One of the cool things about ASP.NET MVC 2’s validation architecture is that it supports both server-side and client-side validation.  To enable this, all we need to do is to add two JavaScript references to our view, and write one line of code:

    image

    When we add these three lines, ASP.NET MVC 2 will use the validation meta-data we’ve added to our Person class and wire-up client-side JavaScript validation logic for us. This means that users will get immediate validation errors when they tab out of an input element that is invalid. 

    To see the client-side JavaScript support in action for our friends application, let’s rerun the application and fill in the first three textboxes with legal values – and then try and click “Create”.  Notice how we’ll get an immediate error message for our missing value without having to hit the server:

    image

    If we enter some text that is not a legal email the error message will immediately change from “Email Required” to “Not a valid email” (which are the error messages we specified when we added the rules to our Person class):

    image

    When we enter a legal email the error message will immediately disappear and the textbox background color will go back to its normal state:

    image

    The nice thing is that we did not have to write any custom JavaScript of our own to enable the above validation logic.  Our validation code is also still very DRY- we can specify the rules in one place and have them be enforced across all across the application – and on both the client and server.

    Note that for security reasons the server-side validation rules always execute even if you have the client-side support enabled.  This prevents hackers from trying to spoof your server and circumvent the client-side rules.

    The client-side JavaScript validation support in ASP.NET MVC 2 can work with any validation framework/engine you use with ASP.NET MVC.  It does not require that you use the DataAnnotation validation approach – all of the infrastructure works independent of DataAnnotations and can work with Castle Validator, the EntLib Validation Block, or any custom validation solution you choose to use.

    If you don’t want to use our client-side JavaScript files, you can also substitute in the jQuery validation plugin and use that library instead.  The ASP.NET MVC Futures download will include support for enable jQuery validation against the ASP.NET MVC 2 server-side validation framework as well.

    Step 4: Creating a Custom [Email] Validation Attribute

    The System.ComponentModel.DataAnnotations namespace within the .NET Framework includes a number of built-in validation attributes that you can use.  We’ve used 4 different ones in the sample above - [Required], [StringLength], [Range], and [RegularExpression].

    You can also optionally define your own custom validation attributes and use them as well.  You can define completely custom attributes by deriving from the ValidationAttribute base class within the System.ComponentModel.DataAnnotations namespace.  Alternatively, you can choose to derive from any of the existing validation attributes if you want to simply extend their base functionality. 

    For example, to help clean up the code within our Person class we might want to create a new [Email] validation attribute that encapsulates the regular expression to check for valid emails.  To do this we can simply derive it from the RegularExpression base class like so, and call the RegularExpression’s base constructor with the appropriate email regex:

    image

    We can then update our Person class to use our new [Email] validation attribute in place of the previous regular expression we used before – which makes the code more clean and encapsulated:

    image

    When creating custom validation attributes you can specify validation logic that runs both on the server and on the client via JavaScript.

    In addition to creating validation attributes that apply to individual properties on an object, you can also apply validation attributes at the class level – which allows you to perform validation logic across multiple properties within an object.  For an example of this in action, you can review the “PropertiesMustMatchAttribute” custom attribute that is included in the AccountModels.cs/vb file within the default ASP.NET MVC 2 application project template (just do a File->New ASP.NET MVC 2 Web Project within VS 2010 and look for this class). 

    Step 5: Persisting to a Database

    Let’s now implement the logic necessary to save our friends to a database. 

    image 

    Right now we are simply working against a plain-old C# class (sometimes referred to as a “POCO” class - “plain old CLR (or C#) object”).  One approach we could use would be to write some separate persistence code that maps this existing class we’ve already written to a database. Object relational mapping (ORM) solutions like NHibernate support this POCO / PI style of mapping today very well.  The ADO.NET Entity Framework (EF) that ships with .NET 4 will also support POCO / PI mapping, and like NHibernate will also optionally enable the ability to define persistence mappings in a “code only” way (no mapping file or designers required). 

    If our Person object was mapped to a database in this way then we wouldn’t need to make any changes to our Person class or to any of our validation rules – it would continue to work just fine. 

    But what if we are using a graphical tool for our ORM mappings?

    Many developers using Visual Studio today don’t write their own ORM mapping/persistence logic – and instead use the built-in designers within Visual Studio to help manage this.

    One question that often comes up when using DataAnnotations (or any other form of attribute based validation) is “how do you apply them when the model object you are working with is created/maintained by a GUI designer”.  For example, what if instead of having a POCO style Person class like we’ve been using so far, we instead defined/maintained our Person class within Visual Studio via a GUI mapping tool like the LINQ to SQL or ADO.NET EF designer:

    image

    Above is a screen-shot that shows a Person class defined using the ADO.NET EF designer in VS 2010.  The window at the top defines the Person class, the window at the bottom shows the mapping editor for how its properties map to/from a “People” table within a database.  When you click save on the designer it automatically generates a Person class for you within your project.  This is great, except that every time you make a change and hit save it will re-generate the Person class – which would cause any validation attribute declarations you make on it to be lost.

    One way you can apply additional attribute-based meta-data (like validation attributes) to a class that is auto-generated/maintained by a VS designer is to employ a technique we call “buddy classes”.  Basically you create a separate class that contains your validation attributes and meta-data, and then link it to the class generated by the designer by applying a “MetadataType” attribute to a partial class that is compiled with the tool-generated class.  For example, if we wanted to apply the validation rules we used earlier to a Person class maintained by a LINQ to SQL or ADO.NET EF designer we could update our validation code to instead live in a separate “Person_Validation” class that is linked to the “Person” class created by VS using the code below:

    image

    The above approach is not as elegant as a pure POCO approach – but has the benefit of working with pretty much any tool or designer-generated code within Visual Studio. 

    Last Step – Saving the Friend to the Database

    Our last step – regardless of whether we use a POCO or tool-generated Person class – will be to save our valid friends into the database. 

    Doing that simply requires us to replace the “Todo” placeholder statement within our FriendsController class with 3 lines of code that saves the new friend to a database.  Below is the complete code for the entire FriendsController class - when using ADO.NET EF to do the database persistence for us:

    image

    And now when we visit the /Friends/Create URL we can easily add new People to our friends database:

    image

    Validation for all the data is enforced on both the client and server.  We can easily add/modify/delete validation rules in one place, and have those rules be enforced by all controllers and views across our application.

    Summary

    ASP.NET MVC 2 makes it much easier to integrate validation into web applications. It promotes a model-based validation approach that enables you to keep your applications very DRY, and helps ensure that validation rules are enforced consistently throughout an application.  The built-in DataAnnotations support within ASP.NET MVC 2 makes supporting common validation scenarios really easy out of the box.  The extensibility support within the ASP.NET MVC 2 validation infrastructure then enables you to support a wide variety of more advanced validation scenarios – and plugin any existing or custom validation framework/engine.

    Hope this helps,

    Scott

  • ASP.NET MVC 2: Strongly Typed Html Helpers

    [In addition to blogging, I am also now using Twitter for quick updates and to share links. Follow me at: twitter.com/scottgu]

    This is the first in a series of blog posts I’m doing on the upcoming ASP.NET MVC 2 release.  This blog post covers the new strongly-typed HTML helpers added with ASP.NET MVC 2.

    Existing HTML Helper Methods

    ASP.NET MVC 1 shipped with a set of HTML helper methods that can be used within view templates to help with the generation of HTML UI.  For example, to output a textbox you could write code (within your .aspx view template) using the Html.TextBox() helper method below:

    image

    The first parameter to the helper method above supplies the name/id for the textbox, and the second parameter specifies the value it should have.  The helper method above would then render HTML like below back to a browser:

    image

    New Strongly-Typed HTML Helper Methods

    One of the common feature asks people had for ASP.NET MVC 2 was for us to also support strongly-typed HTML helpers that use lambda expressions when referencing models/viewmodels passed to a view template.  This enables better compile-time checking of views (so that bugs can be found at build-time as opposed to runtime), and also enables better code intellisense support within view templates.

    New strongly-typed HTML helper methods are now built-into ASP.NET MVC 2.  These methods use a "Html.HelperNameFor()” naming convention. For example: Html.TextBoxFor(), Html.CheckBoxFor(), Html.TextAreaFor(), etc.  They support using a lambda expression to specify both the name/id of the element, as well as the value to render for it.

    For example, using ASP.NET MVC 2 we can now use the new Html.TextBoxFor() helper in addition to the Html.TextBox() helper above:

    image

    Notice above how we do not need to specify the “ProductName” string parameter anymore – lambda expressions are flexible enough that we can retrieve both the name of the property/field on our model object in addition to its value.

    Because the HTML helpers are strongly-typed, we also get full intellisense support for them within Visual Studio when writing the lambda expression:

    image

    The HTML rendered is the same as the late-bound version of our HTML helper shown previously:

    image

    List of Strongly-Typed HTML Helper Methods built-into ASP.NET MVC 2

    ASP.NET MVC 2 has built-in support for the following strongly-typed HTML helpers:

    HTML Element Helpers:

    • Html.TextBoxFor()
    • Html.TextAreaFor()
    • Html.DropDownListFor()
    • Html.CheckboxFor()
    • Html.RadioButtonFor()
    • Html.ListBoxFor()
    • Html.PasswordFor()
    • Html.HiddenFor()
    • Html.LabelFor()

    Other Helpers:

    • Html.EditorFor()
    • Html.DisplayFor()
    • Html.DisplayTextFor()
    • Html.ValidationMessageFor()

    I’ll be covering the new Html.EditorFor() and Html.DisplayFor() helper methods in a later blog post in this series when I cover the improved auto-scaffold functionality in ASP.NET MVC 2.  We’ll also be using the Html.ValidationMessageFor() helper in my next blog post in this series which covers the improved validation support within ASP.NET MVC 2.

    Strongly-Typed HTML Helpers within Scaffolding

    VS 2008 and VS 2010 both by default now use the new strongly-typed HTML helpers when “scaffolding” new strongly-typed view tempates using the “Add View” command. 

    For example, let’s assume we had a simple “ProductsController” class like below that has an “Edit” action method that renders an edit form for a “Product” model class:

    image

    We can right-click within the Edit action method using Visual Studio and choose the “Add View” context menu command to create a view template.  We’ll choose to create an “Edit” template that is scaffolded using a Product object:

    image

    With ASP.NET MVC 2, the view template that is created by default now uses the new strongly typed HTML helper methods to reference the Product model object:

    image

    Summary

    The strongly-typed HTML helpers included with ASP.NET MVC 2 provide a nice way to get better type-safety within your view templates.  This enables better compile-time checking of your views (allowing you to find errors at build-time instead of at runtime), and also supports richer intellisense when editing your view templates within Visual Studio.

    Hope this helps,

    Scott

  • ASP.NET MVC 2

    [In addition to blogging, I am also now using Twitter for quick updates and to share links. Follow me at: twitter.com/scottgu]

    Over the last six months the ASP.NET team has been steadily releasing preview, then beta, and now release candidate builds of ASP.NET MVC 2.

    Given that the final release is not too far away, I thought it was a good time to start a new multi-part ASP.NET MVC 2 blog series that discusses the new features and how best to take advantage of them.

    ASP.NET MVC 2

    We shipped ASP.NET MVC 1.0 last March.  Since then, almost 1 million developers have downloaded and used the final release, and its popularity has steadily grown month over month.

    ASP.NET MVC 2 is the next significant update of ASP.NET MVC. It is a compatible update to ASP.NET MVC 1 – so all the knowledge, skills, code, and extensions you already have with ASP.NET MVC continue to work and apply going forward. Like the first release, we are also shipping the source code for ASP.NET MVC 2 under an OSI-compliant open-source license.

    ASP.NET MVC 2 Features

    ASP.NET MVC 2 adds a bunch of new capabilities and features.  I’ll cover them in a lot more depth with this blog series.  Some of them include:

    • New Strongly Typed HTML Helpers (posted: Jan 10th, 2010)
    • Enhanced Model Validation support across both server and client (posted: Jan 15th, 2010) 
    • Auto-Scaffold UI Helpers with Template Customization (post coming soon)
    • Support for partitioning large applications into “Areas” (post coming soon)
    • Asynchronous Controllers support (post coming soon)
    • Support for rendering sub-sections of a page/site using Html.RenderAction (post coming soon)
    • Lots of new helper functions, utilities, and API enhancements (post coming soon)
    • Improved Visual Studio tooling support (post coming soon)

    How to download ASP.NET MVC 2

    ASP.NET MVC 2 is designed to work with both VS 2008 / .NET 3.5, as well as with VS 2010 / .NET 4.  Supporting both versions means that you can start using it today without having to wait to upgrade to VS2010 / .NET 4.

    Click here to download the ASP.NET MVC 2 release candidate for .NET 3.5 and VS 2008.  It can be installed side-by-side with ASP.NET MVC 1.0 on the same machine.

    ASP.NET MVC 2 is a built-in component of VS 2010 / .NET 4 – which means you will not have to download or install anything to get it once you install any version of Visual Studio 2010.  The current public VS 2010 Beta 2 release includes the ASP.NET MVC 2 Preview 2 release.  The upcoming VS 2010 Release Candidate that will be available for download next month will have a more recent ASP.NET MVC 2 RC built-in.

    ASP.NET Web Forms + ASP.NET MVC

    We are always careful to make clear that ASP.NET MVC is an option with ASP.NET.  ASP.NET Web Forms continues to be the most widely used approach when building applications with ASP.NET, and the new ASP.NET 4 release contains significant improvements for ASP.NET Web Forms development (clean client IDs and CSS based control markup, better viewstate management, new data and charting controls, URL routing, SEO improvements, and much more).  You can learn more about these improvements within my ongoing VS 2010 and .NET 4 blog series.

    We’ll be improving and enhancing both the ASP.NET Web Forms and ASP.NET MVC programming models even further in future releases. Developers can and should choose to use whichever model feels most comfortable and natural to them. We’ll be publishing new videos and guidance on the www.asp.net shortly that helps provide additional guidance about each and how to pick the one that feels most comfortable to you. 

    Hope this helps,

    Scott

  • ASP.NET 4, ASP.NET MVC, and Silverlight 4 Videos of my Talks in Europe

    [In addition to blogging, I’m also now using Twitter for quick updates and to share links. Follow me at: twitter.com/scottgu]

    Hope you all had a great holiday – welcome to 2010!

    Last month I did a blog post about some of the presentations I did in Europe and posted the slides+demo files from them.  High-quality videos of the talks I did in Sweden were posted two weeks ago on the Channel9 site, so you can also now watch videos of the talks online as well.  The videos use a nice format where you can watch me talking as well as the screen at the same time.  The code is readable when running in full-screen mode.

    Below are links to the different talks along with the slides+sample files:

    ASP.NET 4 and VS 2010 Web Development

    This 90 minute talk provides a nice introduction to ASP.NET 4 and VS 2010 for Web Development.  It is primarily demo-driven and walks-through a lot of the new features coming with the release.

    ASP.NET MVC

    This 2 hour talk provides a nice introduction to ASP.NET MVC, and explains it by walking through how to build a simple application with it from scratch.  Along the way it highlights and discusses some of the new features coming in ASP.NET MVC 2. 

    Silverlight 4

    This 60 minute talk recaps the keynote I gave at PDC.  It walks-through the new Silverlight 4 features and capabilities.

    Hope this helps,

    Scott

  • My Presentations in Europe (December 2009)

    This past week I’ve been traveling around Europe giving a bunch of presentations (approximately 5 hours in each country) – Norway on Tuesday, Sweden on Wednesday, Denmark on Thursday, and Belgium on Friday.  I’ll then be presenting at the BizSpark Camp in France this coming Tuesday.

    Things went well with the talks, and I had fun meeting lots of new people (more than 3,000 attended the talks!). Below is a picture of my talk in Belgium – where everyone showed up in a red shirt :-)

    belgium

    Download Talks

    My talks were filmed in a few locations – and I’ll update this post with pointers to the videos once they are online to watch.

    Below are copies of my slides + demos bits:

    Hope this helps,

    Scott

    P.S. In addition to blogging, I’m also now using Twitter for quick updates and to share links. Follow me at: twitter.com/scottgu

  • ASP.NET MVC V2 Preview 1 Released

    The ASP.NET team just released the first public preview of ASP.NET MVC Version 2.  You can download it here.

    Today’s preview works with .NET 3.5 SP1 and VS 2008, and can be installed side-by-side on the same machine as ASP.NET MVC 1.0 (meaning they don’t conflict and your existing ASP.NET MVC 1.0 projects will not be impacted if you install it).  If you have both ASP.NET MVC 1.0 and ASP.NET MVC 2.0 installed you’ll see two ASP.NET MVC project templates within Visual Studio 2008’s “New Project” dialog:

    The release notes that come with the ASP.NET MVC 2 Preview release detail how to upgrade existing ASP.NET MVC 1.0 projects to use V2 if you’d like to migrate them forward to take advantage of the new features.

    New Features

    ASP.NET MVC V2 will include a bunch of new capabilities and features (some of these have already been called out on the ASP.NET MVC roadmap page).  Today’s “Preview 1” release contains a first look at some of the new features.  Many more features will show up in future preview builds.  The Preview 1 bits are still relatively early - the team is releasing today’s build to start receiving and incorporating feedback. 

    Below are some quick details about some of the new Preview 1 capabilities:

    Areas Support

    ASP.NET MVC 2 includes support for a new feature called “areas” that allow you to more easily partition and group functionality across an MVC application.

    Areas provide a means of grouping controllers and views to allow building subsections of a large application in relative isolation to other sections. Each area can be implemented as a separate ASP.NET MVC project which can then be referenced by the main application. This helps manage the complexity when building a large application and facilitates multiple teams working together on a single application together.

    Below is a screen-shot that shows a single solution that has three projects.  One of the projects is named “CompanySite” and includes the core site content, layout and controllers and views. There are then two separate “Area” projects - “Blogs” and “Forums”.  These projects implement the functionality that exists under the /Blogs and /Forums URL sections of the site – and encapsulate all of the routing rules, controllers and views implementing these sections:

    The Preview 1 release includes the first part of the areas feature implementation.  It doesn’t include any tool support yet (right now you need to manually add a build task to create an area project and set it up).  Future preview releases will include tooling support, and expand and refine the feature-set further.

    DataAnnotation Validation Support

    ASP.NET MVC 2 now includes built-in support for the DataAnnotation validation support that first shipped with .NET 3.5 SP1 – and which is used with ASP.NET Dynamic Data and .NET RIA Services.  DataAnnotations provides an easy way to declaratively add validation rules to Model and ViewModel classes within an application, and have automatic binding and UI helper validation support within ASP.NET MVC.

    To see this feature in action, we can create a new “Customer” ViewModel class like below that has five properties on it (implemented using the C# automatic property feature).

    We can then decorate the properties with appropriate validation rules using the DataAnnotation attributes implemented within the System.ComponentModel.DataAnnotations namespace.  The code below uses 4 different built-in validation rules – [Required], [StringLength], [Range], and [RegularExpression].  The namespace also includes a base class (ValidationAttribute) that you can subclass to create your own custom validation attributes.

    We can then create a CustomersController class that has two Create action methods on it.  The first Create action method handles HTTP GET requests to the “/Customers/Create” URL, and renders a view template based on an empty Customer object.  The second Create action method handles HTTP POST requests to the same URL (and takes a Customer object as a method parameter).  It checks if there are any model binding errors to the input submitted, and if there are errors it redisplays the view template using the already entered data.  If there are no errors it displays a success view to the user:

    Finally, we can right-click within either of the Create action methods above, choose the “Add View” context menu command, and automatically “scaffold” a “create” view template that is based on the Customer object.  When we do this the generated scaffolded view template will contain the below HTML <form> for our Customer:

    And now when we request the “/Customers/Create” URL in our browser we’ll get an initial empty form like below:

    If we enter invalid input and perform a post to the server, the ASP.NET MVC 2 model binder will detect that there are DataAnnotations attributes on our Customer class, and automatically validate the posted form input using them.  If there are errors our controller action method redisplays the form – which will cause the appropriate validation error messages to be rendered to the user like below.  Note how the validation property error message strings we specified using the DataAnnotation attributes are displayed to the user by the Html.Validation helper methods.  No extra code is required to enable this.

    The above form will redisplay with error messages each time the user enters invalid input and attempts to perform a form post.

    In a future ASP.NET MVC 2 preview we are planning to ship the jQuery Validation plugin as part of the default project template, and add support for the automatic client-side JavaScript enforcement of DataAnnotation validation rules as well.  This will enable developers to easily add validation rules in one place on either a Model or ViewModel object, and have them be enforced both client and server-side everywhere it is used within the application.

    If you do not wish to annotate your model or viewmodel classes directly, you can alternatively create a “buddy class” that accompanies your model class and encapsulates the DataAnnotaton rules separately.  This capability is also useful for scenarios where VS is code-generating/updating the properties on a class directly and you cannot easily add attributes to the generated code (for example: classes generated by the LINQ to SQL or LINQ to Entities designers). 

    In addition to providing built-in support for DataAnnotations, the DefaultModelBinder class in ASP.NET MVC V2 now has new virtual methods that can be overridden to easily integrate other validation frameworks as well (for example: Castle Validator, EntLib Validation, etc).  The validation UI helper methods in ASP.NET MVC are designed to support any type of validation framework (they have no direct knowledge of DataAnnotations).

    Strongly Typed UI Helpers

    ASP.NET MVC V2 includes new HTML UI helpers that enable you to use strong-typed lambda expressions when referencing the view template’s model object.  This enables better compile-time checking of views (so that bugs can be found at build-time as opposed to runtime), and also enables better code intellisense support within view templates.

    You can see an example of the better intellisense in action below – notice how I am getting a full listing of the customer model object’s properties when using the new Html.EditorFor() helper method:

    Preview 1 has built-in support for new Html.EditorFor(), Html.LabelFor(), and Html.DisplayFor() helpers.  An updated MVC futures assembly that we are shipping this week adds additional Html.TextBoxFor(), Html.TextAreaFor(), Html.DropDownListFor(), Html.HiddenFor(), and Html.ValidationMessageFor() helper methods as well (overtime these will move into the core ASP.NET MVC 2 assembly too).

    Below you can see an updated version of the “create” view template for our customer creation scenario.  Notice how instead of using string expressions to reference the customer object we are instead using strongly-typed lambda expressions with the UI helpers.  We can get full intellisense and compile-time checking with all of them:

    The Html.LabelFor() helper method above generates <label for="Name">Name:</label> HTML markup.

    The Html.EditorFor() helper method can be used for any datatype value.  By default it is smart and will output an appropriate HTML <input/> element based on the type to be edited.  For example, it will generate <input type=”text”/> elements for the first four properties above (which are strings and integers).  It will generate a <input type=”checkbox”/> element for the final “IsActive” property – which is of type boolean.

    In addition to supporting simple data-types, the Html.EditorFor() helper method also allows you to pass more complex objects with multiple properties to it.  By default it will loop over the public properties of the object and generate a <label>, <input/> element, and any appropriate validation message for each property it finds.  For example, we could re-write the above view to have just a single Html.EditorFor() call for the Customer object to conceptually output the same markup as above:

    The strongly typed helpers allow you to optionally decorate the properties of the Customer ViewModel class with [DisplayName] attributes to control the label string that is output for each property used (for example: instead of having a label text of “IsActive” we could apply a [DisplayName(“Is Active Customer:”)] attribute). 

    You can also add [ScaffoldColumn(false)] attributes to indicate that a particular property shouldn’t be rendered at all in scenarios like above where complex objects are passed to Html.EditorFor().

    UI Helper Templating Support

    The Html.EditorFor() and Html.DisplayFor() helper methods have built-in support for rendering both standard data-types as well as complex objects with multiple properties.  As noted above, they also support basic customization of rendering by applying attributes like [DisplayName] and [ScaffoldColumn] to the ViewModel.

    Often developers want to be able to customize the output from UI helpers even further, though, and have total control over what is generated.  The Html.EditorFor() and Html.DisplayFor() helper methods support this via a templating mechanism that allows you to define external templates that can override and completely control the output rendered.  Better yet, you can customize the content rendered on a per-datatype/class basis.

    With Preview 1 you can now optionally add an “EditorTemplates” and/or “DisplayTemplates” folder underneath either a \Views\[controllername] directory (if you want to customize the rendering for views used by a specific controller) or underneath the \Views\Shared folder (if you want to customize the rendering for all views and controllers in an application). 

    You can then add partial template files to these folders to customize the output rendering performed on an individual datatype and/or class basis.  For example, below I have added an EditorTemplates folder underneath the \Views\Shared folder – and added three custom template files to it:

    The “Customer.ascx” template above indicates that I want to customize the output anytime Html.EditorFor() is passed a Customer object (for example: I could customize the exact ordering/layout of the Customer properties).  The “DateTime.ascx” template above indicates that I want to customize the output anytime Html.EditorFor() is passed a DateTime property (for example: I might want to use a JavaScript datepicker instead of a plain textbox).  I could optionally add an “Object.ascx” template to the folder if I wanted to override the default rendering of all objects.

    In addition to customizing rendering on a per-type basis, you can also add “named templates” to the folder.  A common scenario might be a “CountryDropDown” template that handles a string datatype – but instead of providing a standard textbox instead renders a <select> dropdownlist of country values that a user can pick from.  Below is what this editor template might look like:

    We can explicitly indicate that we want to use the above template by passing its name as an argument when we invoke the Html.EditorFor() helper method.  For example, below in addition to specifying a lambda expression for our Country property, we are also specifying the name of the editor template to use when rendering it:

    Alternatively, you can specify “UIHint” attributes on your ViewModel properties and types.  This allows you to indicate the default editor or display template to use in a single place, and have it be used in all views across your application (without having to explicitly pass it as an argument to Html.EditorFor). 

    Below is an example of how to indicate using a UIHint attribute that the Customer.Country property (which is of type string) should by default use the CountryDropDown template when being rendered:

    Once we set the above attribute on our ViewModel we no longer need to specify a template name explicitly when we use that property with Html.EditorFor().  And now when we hit refresh on our /Customers/Create URL our Country property will be rendered as a dropdown instead of a standard textbox:

    Other Cool Features

    ASP.NET MVC 2 Preview 1 includes a number of other small, but really nice, feature additions.  A few of my favorites include:

    New [HttpPost] Attribute

    It is pretty common with ASP.NET MVC to split up the handling of a URL across two action methods – one that handles GET requests and one that handles POST requests.

    With ASP.NET MVC 1 you used an [AcceptVerbs(HttpVerbs.Post)] attribute to indicate the “Post” version of an action method:

    This still works with ASP.NET MVC 2. Alternatively, though, you can also now take advantage of a terser [HttpPost] attribute that does the same thing:

    Default Parameter Values

    Handling optional parameters is a pretty common web scenario.  With ASP.NET MVC 1 you could handle optional parameters either by registering a custom routing rule and specifying a default value with it, or by marking an action method parameter as nullable and then adding code within your action method to handle whether it was null (and if so provide a default value).

    ASP.NET MVC 2 Preview 1 now supports decorating action method parameters with the DefaultValueAttribute from the System.ComponentModel namespace.  This allows you to specify a parameter value that ASP.NET MVC should pass in if it is not present as part of the request.  For example, below is an example of how we could handle both the /Products/Browse/Beverages and /Products/Browse/Beverages?page=2 URLs – and have the “page” parameter value be “1” if it isn’t provided as part of the querystring:

    VB today allows you to specify default parameter values directly within the VB language (avoiding the need to explicitly specify the DefaultValue attribute like above).  C# in VS2010 will also support default values with optional parameters – which will enable you to rewrite the above code simply as:

    This should make handling default/optional scenarios really easy and clean.

    Binding Binary Data

    ASP.NET MVC Preview 1 adds support for binding base64-encoded string values to properties of type byte[] and System.Data.Linq.Binary.  There are now two overloaded versions of Html.Hidden() that can take these data-types.  These can be useful for scenarios where you want to enable concurrency control within your application and want to roundtrip timestamp values of database rows within your forms. 

    Summary

    Click here to download a .zip file that contains a ASP.NET MVC 2 project that implements the sample code I demonstrated in the above walkthrough.

    Today’s build of ASP.NET MVC 2 is just a first preview.  More features will be coming in future previews, and the team expects to get a lot of feedback on ways to improve and enhance the release. 

    The goal with doing these regular previews is to help make sure that this feedback process is open and that anyone who wants to participate can easily get involved.  Please post any feedback, suggestions or problems you have to the ASP.NET MVC Forum on www.asp.net.  You can also learn more about the release from Phil Haack’s MVC2 post, and from the Channel9 video Phil did with Scott Hanselman about the Preview 1 release.

    Hope this helps,

    Scott

    P.S. I have been using Twitter more recently to-do quick posts and share links.  You can follow me on Twitter at: http://www.twitter.com/scottgu (@scottgu is my twitter name)

  • June 7th Links: ASP.NET, AJAX, ASP.NET MVC, Visual Studio

    Here is the latest in my link-listing series.  Also check out my ASP.NET Tips, Tricks and Tutorials page and Silverlight Tutorials page for links to popular articles I've done myself in the past.

    You can also now follow me on twitter (@scottgu) where I also post links and small posts.

    ASP.NET

    • GridView Confirmation Box using jQuery: Mohammed Azam has a nice post that describes how to implement model confirmation UI using jQuery.  This is particularly useful for scenarios like saving or deleting data.

    AJAX

    • ASP.NET 4.0 AJAX – Client Templates: Damien White has a great post that describes the new client templating support in ASP.NET AJAX.  This provides an easy and powerful way to dynamically create rich HTML UI on the client.

    • ASP.NET 4.0 AJAX - Data Binding: Damien White continues his great ASP.NET AJAX series with this article that describes the new client-side data binding features in the new version of ASP.NET AJAX. 

    ASP.NET MVC

    • DataAnnotations and ASP.NET MVC: Brad Wilson (a dev on the ASP.NET MVC team) has a nice post that describes how to use DataAnnotations to annotate model objects, and then use a model binder to automatically validate them when accepting form posted input.  DataAnnotation support will be built-in with the next version of ASP.NET MVC.

    Visual Studio

    Hope this helps,

    Scott

  • May 30th Links: ASP.NET, AJAX, ASP.NET MVC, Visual Studio

    Here is the latest in my link-listing series.  Also check out my ASP.NET Tips, Tricks and Tutorials page and Silverlight Tutorials page for links to popular articles I've done myself in the past. 

    You can also now follow me on twitter (@realscottgu) where I also post links and small posts.

    ASP.NET

    AJAX

    • Automatically Minify and Combine JavaScript in Visual Studio: Dave Ward has a great article that describes how you can add a build command to Visual Studio that enables you to automatically compress and combine client-side JavaScript files.  This makes your pages load faster on the client and improves the perceived performance of your sites.

    • Client-side Data Binding in ASP.NET AJAX 4.0: Fritz Onion has a great article about the new client-side templating features of ASP.NET AJAX 4.0 (which you can download and use today in .NET 3.5 projects).  This enables powerful client data-binding scenarios against JSON based data.  Also check out Politian’s Blog to find some great tutorials on how to use it.

    ASP.NET MVC

    • Visual Studio NUnit Templates for ASP.NET MVC: The VS Web Tools team has released updated NUnit templates that work with ASP.NET MVC 1.0.  This enables you to automatically create a test project that uses NUnit instead of MSTest when you do a File->New Project and select the ASP.NET MVC 1.0 Project item.

    • Custom Route Constraints in ASP.NET MVC: Keyvan Nayyeriu has a nice post that discusses how to create a custom route constraint in ASP.NET MVC (one of the extensibility points in Simone’s list above).  You can use these to control whether a route rule is used or not, and they can enable some pretty rich routing scenarios.  Note that in addition to creating route constraint classes, ASP.NET MVC also supports using Regular Expressions and HTTP Method filters to constrain routes as well. Keyvan is the co-author with Simone of the Beginning ASP.NET MVC Book (free chapter available).

    Visual Studio

    Hope this helps,

    Scott

  • Free ASP.NET MVC “NerdDinner” Tutorial Now in HTML

    Last month I blogged about a free end-to-end ASP.NET MVC tutorial called “NerdDinner” that I wrote for the Professional ASP.NET MVC 1.0 book from Wrox Press.  The book is now released and shipping on Amazon

    The NerdDinner tutorial walks through how to build a small, but complete, application using ASP.NET MVC, and introduces some of the core concepts behind it.  You can download a PDF version of the tutorial here.

    NerdDinner Tutorial Now Also Available in HTML

    A few minutes ago I finished publishing an HTML version of the NerdDinner tutorial as well.  You can read it online for free here.

    I split the tutorial up across 12 segments to make it more manageable to read.  I also increased the sizes of the screenshots, and used a really nifty syntax highlighter that Scott Hanselman helped set me up with.  I actually find the end result a lot easier to read than the PDF version.

    Below are links to the different NerdDinner tutorial segments:

    Hope this helps,

    Scott

  • ASP.NET MVC 1.0

    mvcsource[1] Two weeks ago at MIX we released ASP.NET MVC 1.0.  ASP.NET MVC is a free, fully supported, Microsoft product that enables developers to easily build web applications using a model-view-controller pattern.  ASP.NET MVC provides a “closer to the metal” web programming option for ASP.NET.  It enables full control over HTML markup and URL structure, and facilitates unit testing and a test driven development workflow.

    Releasing the ASP.NET MVC source code under MS-PL

    I’m excited today to announce that we are also releasing the ASP.NET MVC source code under the Microsoft Public License (MS-PL).  MS-PL is an OSI-approved open source license.  The MS-PL contains no platform restrictions and provides broad rights to modify and redistribute the source code.  You can read the text of the MS-PL at: http://www.opensource.org/licenses/ms-pl.html

    Learning more about ASP.NET MVC

    To learn more about ASP.NET MVC, you can read my free ASP.NET MVC PDF tutorial that covers building an end-to-end application (starting literally with File->New Project).

    There were a number of great ASP.NET MVC talks at MIX this year.  Below are links to several of them:

    There are also several great ASP.NET MVC tutorials at http://www.asp.net/mvc.  You can also read the ASP.NET MVC MSDN Documentation.

    Download ASP.NET MVC

    Click here to download and install ASP.NET MVC 1.0.  You can also install it using the new Microsoft Web Platform Installer V2 – which provides an integrated setup experience for the entire Microsoft web stack.

    The ASP.NET MVC 1.0 source code is now available.  Scroll down to the bottom of the ASP.NET MVC download page and you’ll find links to both the ASP.NET MVC 1.0 integrated MSI setup, as well as a .zip file that contains the ASP.NET MVC source code.  The ASP.NET MVC source code includes a VS 2008 project file that enables you to build it.

    Hope this helps,

    Scott

  • Free ASP.NET MVC eBook Tutorial

    bookcover[1] There has been a lot of excitement in the community about the new ASP.NET MVC framework that is about to ship (literally any day now – announcement coming soon).  As with anything new, people are also asking for more tutorials/samples/documentation that cover how to get started and build applications with it.

    Over the last few months I’ve been helping to contribute to an ASP.NET MVC book that Scott Hanselman, Rob Conery, and Phil Haack have been writing for Wrox.  The book is now in production, and will be available to buy in stores soon (you can pre-order it on Amazon today).

    I wrote the first chapter of the book – which is a 185 page end-to-end tutorial that walks-through building a small, but complete, ASP.NET MVC application from scratch.  The agreement I made with Wrox was that I’d write it for free in return for them also making it available as a free PDF download.

    I’m excited to announce that you can now download this free end-to-end tutorial chapter (it is a 14mb PDF file). It’s licensed under a “Creative Commons Attribution No Derivatives” license – which means you can share, distribute, print, or hand it out to anyone.

    NerdDinner ASP.NET MVC Tutorial

    The tutorial starts by using the File->New Project command in Visual Studio to create a brand new ASP.NET MVC project, and then incrementally adds functionality and features.  Along the way it covers how to:

    • Create a database
    • Build a model with validation and business rules
    • Implement data listing/details UI on a site using Controllers and Views
    • Enable CRUD (Create, Update, Delete) data form entry
    • Use the ViewModel pattern to pass information from a Controller to a View
    • Re-use UI across a site using partials and master pages
    • Implement efficient data paging
    • Secure an application using authentication and authorization
    • Use AJAX to deliver dynamic updates
    • Use AJAX to add interactive map support
    • Perform automated unit testing (including dependency injection and mocking)

    The application the tutorial builds is called “NerdDinner”. It provides an easy way for people to organize, host and search for new topic-based dinners online:

    nerddinner_small[1]

    Scott Hanselman has been hosting NerdDinners for years, and came up with the idea of building the tutorial around an application that facilitates this.  He is also now hosting a live custom-skinned version of the application at www.nerddinner.com)

    Download Links

    Hope this helps,

    Scott

    P.S. The book is entering production now and so is officially in un-edited status (meaning professional editors haven’t gone through it yet).  We’ll update the PDF with any important edits once the text is final.

    P.P.S. And yes – this is one of the reasons my blog has been more quiet than normal the last few months.  Expect more regular blog posting again soon once I recover from this. :-)

  • ASP.NET MVC 1.0 Release Candidate Now Available

    Today we shipped the ASP.NET MVC 1.0 Release Candidate (RC).  Click here to download it (or visit www.asp.net/mvc).  It works with both Visual Studio 2008 and Visual Web Developer 2008 (which is free).

    Today’s RC is the last public release of ASP.NET MVC that we’ll ship prior to the final “1.0” release.  We expect to ship the final ASP.NET MVC 1.0 release next month.

    In addition to bug fixes, today’s build includes several new features.  It also includes some refinements to existing features based on customer feedback.  Please read the release notes that ship with the ASP.NET MVC download for full details on all changes.  The release notes include detailed instructions on how to upgrade existing applications built with the ASP.NET MVC Beta to the RC.

    Visual Studio Tooling Improvements

    The RC includes several new Visual Studio tooling features (above and beyond the existing support in the beta – which I won’t cover here).  These features include:

    Add Controller Command

    You can now type Ctrl-M, Ctrl-C within an ASP.NET MVC project, or right-click on the /Controller folder and choose the “Add->Controller” context menu item to create new controller classes:

    This will cause an “Add Controller” dialog to appear that allows you to name the Controller to create, as well as optionally indicate whether you wish to automatically “scaffold” common CRUD methods:

    Clicking the “Add” button will cause the controller class to be created and added to the project:

    Add View Command

    You can now type Ctrl-M, Ctrl-V within a Controller action method, or right-click within an action method and choose the “Add View” context menu item to create new view templates:

    This will cause an “Add View” dialog to appear that allows you to name and create a new view (it is pre-populated with convention-based options).  It allows you to create “empty” view templates, or automatically generate/scaffold view templates that are based on the type of object passed to the view by the Controller action method.  The scaffolding infrastructure uses reflection when creating view templates – so it can scaffold new templates based on any POCO (plain old CLR object) passed to it.  It does not have a dependency on any particular ORM or data implementation.

    For example, below we are indicating that we want to scaffold a “List” view template based on the sequence of Product objects we are passing from our action method above:

    Clicking the “Add” button will cause a view template to be created for us within the \Views\Products\ directory with a default “scaffold” implementation:

    We can then run our application and request the /products URL within our browser to see a listing of our retrieved products:

    The RC ships with a number of built-in scaffold templates: “Empty”, “List”, “Details”, “Edit” and “Create” (you can also add your own scaffold templates – more details on this in a moment). 

    For example, to enable product editing support we can implement the HTTP-GET version of our “Edit” action method on our Products controller like below and then invoke the “Add View” command:

    Within the “Add View” dialog we can indicate we are passing a “Product” object to our view and choose the “Edit” template option to scaffold it:

    Clicking the “Add” button will cause an edit view template to be created with a default scaffold implementation within the \Views\Products\ directory:

    We can then run our application and request the /products/edit/1 URL within our browser to edit the Product details:

    To save edit changes we can implement the HTTP-POST version of our “Edit” action method on our Products controller:

    Notice in the code above how in the case of an error (for example: someone enters a bogus string for a number value) we redisplay the view.  The “edit” and “create” scaffold templates contain the HTML validation helper methods necessary to preserve user input and flag invalid input elements in red when this happens:

    You’ll rarely end up using a scaffold-created template exactly as-is, and often will end up completely replacing it.  But being able to get an initial implementation up and running quickly, and having an initial view template for your scenario that you can then easily tweak is really useful.

    Because the scaffold infrastructure supports scaffolding views against any plain-old CLR object, you can use it with both domain model objects (including those mapped with LINQ to SQL, LINQ to Entities, nHibernate, LLBLGen Pro, SubSonic, and other popular ORM implementations) as well as to create scaffolds with custom Presentation Model/ViewModel classes.

    Adding and Customizing Scaffold Templates

    ASP.NET MVC’s scaffolding infrastructure is implemented using Visual Studio’s built-in T4 templating architecture (Scott Hanselman has a nice blog post on T4 here). 

    You can customize/override any of the built-in ASP.NET MVC scaffold template implementations.  You can also create additional scaffold templates (for example: the “ScottGu Crazy Look” scaffold option) and have them be displayed as options within the “Add View” dialog.

    To customize/add scaffold templates at the machine-wide level, open the “C:\Program Files\Microsoft Visual Studio 9.0\Common7\IDE\ItemTemplates\CSharp\Web\MVC\CodeTemplates” folder:

    The “AddController” sub-folder contains the scaffold template for the “Add Controller” dialog.  The “AddView” sub-folder contains the scaffold templates for the “Add View” dialog:

    The scaffold templates populated within the “Add View” dialog are simply text files that have the “.tt” file-name extension.  These “.tt” text files contain inline C# or VB code that executes when the template is selected. 

    You can open and edit any of the existing files to customize the default scaffolding behavior.  You can also add new “.tt” template files – like I have above with the “Scott Crazy Look.tt” file.  When you add a new template file the “Add View” dialog will be updated to automatically include it in the list of available scaffold options:

    In addition to customizing/adding template files at the machine level, you can also add/override them at the individual project level.  This also enables you to check-in the templates under source control and easily use them across a team.

    You can customize the scaffold templates at a project level by adding a “CodeTemplates” folder underneath your project.  You can then have “AddController” and “AddView” sub-folders within it:

    You can override any of the default machine-wide templates simply be adding a “.tt” file with the same name to the project.  For example, above we are overriding the default “Controller.tt” scaffold template used in “Add Controller” scenarios. 

    You can add new view-template scaffold files to the list by placing them within the “AddView” folder.  For example, above we added a “Yet Another Crazy Look.tt” view template to our project.  When we use the “Add View” dialog we’ll now see a union of the templates defined at the machine and project level:

    Note: When you add “.tt” templates under the \CodeTemplates folder make sure to set the “Custom Tool” property of each of the “.tt” template files to an empty string value within the property grid (otherwise you’ll get an error trying to run it).  You might also need to close and reopen the project to clear a spurious error from the error list.  We’ll be publishing more blog posts that cover creating/customizing scaffolding templates shortly.

    Go To Controller / Go To View

    The RC build now supports the ability to quickly navigate between the Controllers and Views within your projects. 

    When your cursor is within a Controller action method you can type Ctrl-M, Ctrl-G to quickly navigate to its corresponding view template.  You can also perform this same navigation jump by right-clicking within the action method and selecting the “Go To View” menu option:

    In the example above we used the “Go To View” command within the “Edit” action method of the ProductsController class.  This will cause the \Views\Products\Edit.aspx view template to be opened and have the default focus within VS:

    Within view templates you can also now type Ctrl-M, Ctrl-G to quickly navigate to the view’s corresponding Controller class.  You can also perform this navigation jump by right-clicking within the view template and selecting the “Go To Controller” menu option:

    MSBuild Task for Compiling Views

    By default when you do a build on an ASP.NET MVC project it compiles all code within the project, except for the code within view template files.  With the ASP.NET MVC Beta you had to roll your own MSBuild task if you wanted to compile the code within view templates.  The ASP.NET MVC RC build now includes a built-in MSBuild task that you can use to include views as part of the project compilation process.  This will verify the syntax and code included inline within all views, master pages, and partial views for the application, and give you build errors if it encounters any problems.

    For performance reasons we don't recommend running this for quick compiles during development, but it is convenient to add to particular build configuration profiles (for example: staging and deployment) and/or for use with Build or CI (continuous integration) servers.  Please review the release notes for the steps to enable this.

    View Refactoring Support

    The names of the files and folders under the \Views application sub-folder will now automatically be updated when you perform controller class rename or action method rename using the “Rename” refactoring command in VS 2008.  VS 2008 will apply the standard convention-based naming pattern to existing view files/folders when the Controller class is updated.

    View Improvements

    The RC build includes a number of view-specific enhancements that were incorporated based on feedback during the preview releases.

    Views without Code-Behind Files

    Based on feedback we’ve changed view-templates to not have a code-behind file by default.  This change helps reinforce the purpose of views in a MVC application (which are intended to be purely about rendering and to not contain any non-rendering related code), and for most people eliminates unused files in the project.

    The RC build now adds C# and VB syntax support for inheriting view templates from base classes that use generics.  For example, below we are using this with the Edit.aspx view template – whose “inherits” attribute derives from the ViewPage<Product> type:

    One nice benefit of not using a code-behind file is that you'll now get immediate intellisense within view template files when you add them to the project.  With previous builds you had to do a build/compile immediately after creating a view in order to get code intellisense within it.  The RC makes the workflow of adding and immediately editing a view compile-free and much more seamless.

    Important: If you are upgrading a ASP.NET MVC project that was created with an earlier build make sure to follow the steps in the release notes – the web.config file under the \Views directory needs to be updated with some settings in order for the above generics based syntax to work.

    Model Property

    With previous builds of ASP.NET MVC, you accessed the strongly typed model object passed to the view using the ViewData.Model property:

    The above syntax still works, although now there is also a top-level "Model" property on ViewPage that you can also use:

    This property does the same thing as the previous code sample - its main benefit is that it allows you to write the code a little more concisely.  It also allows you to avoid using the ViewData dictionary in cases where you want the view template to only interact with the strongly-typed model passed to it.

    Setting the Title

    The default master-page template added to new ASP.NET MVC projects now has an <asp:contentplaceholder/> element within its <head> section.  This makes it much easier for view templates to control the <title> element of the HTML page rendered back – and not require the Controller to explicitly pass a “title” parameter to configure it (which was the default with previous ASP.NET MVC builds and we thought questionable from a responsibilities perspective). 

    For example, to customize the <title> of our Edit view to include the current product name we can now add the below code to our Edit.aspx template to drive the title directly off of the model object being passed the view:

    The above code will then cause the browser to render the title using the Product name at runtime:

    In addition to setting the <title> element, you can also use the above approach to dynamically add other <head> elements at runtime.  Another common scenario this is useful with is configuring model/view specific <meta/> elements for search engine optimization. 

    Strongly Typed HTML/AJAX Helpers

    One of the requests a few people have asked for is the ability to use strongly-typed expression syntax (instead of strings) when referring to the Model when using a View's HTML and AJAX helper objects.

    With the beta build of ASP.NET MVC this wasn't possible, since the HtmlHelper and AjaxHelper helper classes didn't expose the model type in their signature, and so people had to build helper methods directly off of the ViewPage<TModel> base class in order to achieve this. 

    The ASP.NET MVC RC build introduces new HtmlHelper<TModel> and AjaxHelper<TModel> types that are exposed on the ViewPage<TModel> base class.  These types now allow anyone to build strongly-typed HTML and AJAX helper extensions that use expression syntax to refer to the View's model.  For example:

    The HTML form helper extension methods in the core ASP.NET MVC V1 assembly still use the non-expression based string syntax.  The “MVC Futures” assembly released today (which works with the RC) has a few initial implementations of expression-syntax based form helper methods.   We are going to iterate on these a bit longer and then consider adding them into the ASP.NET MVC core assembly in the next release. 

    You can of course also add your own helper methods (using either strings or strongly-typed BLOCKED EXPRESSION.  The built-in HTML/AJAX helper methods can also optionally be removed (because they are extension methods) if you want to replace or override them with your own

    Form Post Improvements

    The RC build includes a number of form-post specific enhancements:

    [Bind(Prefix=””)] No Longer Required for Common Scenarios

    The RC build no longer requires you to explicitly use a [Bind] attribute (or set its prefix value to “”) in order to map incoming form post parameters that do not have a prefix to complex action method parameters.

    To see what this means, let’s implement the “Create” scenario for our ProductsController.  We’ll begin by implementing the HTTP-GET version of our “Create” action method.  We’ll do this with code below that returns a View based on an empty Product object:

    We can then right-click within our action method, choose the “Add View” command and scaffold a “create” view template that is based on a Product:

    Notice above how our Html.TextBox() helper methods are referencing the “ProductName” and “SupplierID” properties on our Product object.  This will generate HTML markup like below where the input “name” attributes are “ProductName” and “SupplierID”:

    We can then implement the HTTP-POST version of our “Create” action method. We’ll have our action method take a Product object as a method parameter:

    With the ASP.NET MVC Beta we would have had to add a [Bind(Prefix=””)] attribute in front of our Product argument above – otherwise the ASP.NET MVC binding infrastructure would have only looked for form post values with a “productToCreate.” prefix (for example: productToCreate.ProductName and productToCreate.SupplierID) and not found the submitted values from our form (which don’t have a prefix). 

    With the RC build, the default action method binders still first attempt to map a productToCreate.ProductName form value to the Product object.  If they don’t find such a value, though, they now also attempt to map “ProductName” to the Product object.  This makes scenarios where you pass in complex objects to an action method syntactically cleaner and less verbose.  You can take advantage of this feature both when mapping domain objects (like our Product object above) as well as with Presentation Model/ViewModel classes (like a ProductViewModel class).

    A completed implementation of our Create action method (including basic input type error handling) might look like below:

    Now our create action will save the Product object if all values are entered correctly.  When a user attempts to create a Product with invalid Product property values (for example: a string “Bogus” instead of a valid Decimal value), the form will redisplay and flag the invalid input elements in red:

    ModelBinder API Improvements

    The model binding infrastructure within the ASP.NET MVC Release Candidate has been refactored to add additional extensibility points to enable custom binding and validation schemes.  You can read more about these details in the ASP.NET MVC RC release notes.

    Model Binders can also now be registered for interfaces in addition to classes. 

    IDataErrorInfo Support

    The default model binder with ASP.NET MVC now supports classes that implement the IDataErrorInfo interface.  This enables a common approach to raise validation error messages in a way that can be shared across Windows Forms, WPF and now ASP.NET MVC applications.

    Unit Testing Improvements

    The ASP.NET MVC RC includes some significant improvements to unit testing:

    ControllerContext changed to no longer derive from RequestContext

    The RC build includes a refactoring of the ControllerContext class that significantly simplifies common unit testing scenarios.  The ControllerContext class no longer derives from RequestContext and now instead encapsulates RequestContext and exposes it as a property.  The properties of ControllerContext and its derived types are also now virtual instead of sealed – making it significantly easier to create mock objects.

    To see how this helps, let’s consider an action method like below that uses both the “Request” and “User” intrinsic objects:

    Testing the above action method with previous ASP.NET MVC builds would have required mocking RequestContext and ControllerContext (with some non-obvious constructors that also brought in a RouteData object).

    With the RC build we can now unit test it like below (using Moq to mock a ControllerContext for our Controller that allows us to simulate the Request.IsAuthenticated and User.Identity.Name properties):

    The refactoring improvements made help out not just with testing Controller actions – but also help with testing filters, routes, custom actionresult types, and a variety of other scenarios.

    AccountsController Unit Tests

    The ASP.NET MVC Project Template included with the RC build now adds 25 pre-built unit tests that verify the behavior of the AccountsController class (which is a controller added to the project by default to handle login and account management scenarios).  This makes refactoring/updating AccountsController easier.  The AccountsController implementation has also been modified to more easily enable non-Membership Provider based credential systems to be integrated.

    Cross Site Request Forgery (CSRF) Protection

    Cross-site request forgery (CSRF) attacks (also referred to as XSRF attacks) cause users of a trusted browser agent to take unintended actions on a site.  These attacks rely on the fact that a user might still be logged in to another site.  A malicious Web site exploits this by creating a request to the original site (for example: by linking to a URL on the site using a <img src=””/> element on the hacker site). The request is made using the user’s browser and thus with the user’s authentication token and credentials. The attacker hopes that the user’s authentication or session cookie is still valid and if so, the attacker can sometimes take disruptive action.  You can learn more about this hacking technique here.

    The ASP.NET MVC RC now includes some built-in CSRF protection helpers that can help mitigate CSRF attacks.  For example, you can now use the Html.AntiForgeryToken() helper to render a hidden input token within forms:

    This helper issues a HTTP cookie and renders a hidden input element into our form.  Malicious web-sites will not be able to access both values.

    We can then apply a new [ValidateAntiForgeryToken] attribute onto any action method we want to protect:

    This will check for the existence of the appropriate tokens, and prevent our HTTP-POST action method from running if they don’t match (reducing the chance of a successful CSRF attack).

    File Handling Improvements

    The ASP.NET MVC RC includes a number of file handling enhancements:

    FileResult and File() helper method

    The RC build adds a new FileResult class that is used to indicate that a file is being returned as an ActionResult from a Controller action method.  The Controller base class also now has a set of File() helper methods that make it easy to create and return a FileResult.

    For example, let’s assume we are trying to build a photo management site.  We could define a simple “Photo” class like below that encapsulates the details about a stored Photo:

    We could then use the new File() helper method like below to implement a “DisplayPhoto” action method on a PhotoManager controller that could be used to render the Photo out of a database store.  In the code below we are passing the File() helper the bytes to render, as well as the mime-type of the file. If we pointed a <img src=””/> element at our action method URL the browser would display the photo inline within a page:

    If we wanted an end-user to be able to download the photo and save it locally, we could implement a “DownloadPhoto” action method like below.  In the code below we are passing a third parameter – which will cause ASP.NET MVC to set a header that causes the browser to display a “Save As…” dialog which is pre-populated with the filename we’ve supplied:

    When a user clicks a link to the /PhotoManager/DowloadPhoto/1232 URL they’ll be prompted to save the picture:

    File Uploading Support

    The RC build also includes built-in model-binder support for uploaded files and multi-part mime content. 

    For example, we could have a <form> whose enctype attribute is set to “multipart/form-data” perform a post to the /PhotoManager/UploadPhoto URL.  If a <input type=”file” name=”fileToUpload”/> element was within the form it would cause the file selected by the end-user to be passed to our action method as an HttpPostedFileBase object:

    We could then use the HttpPostedFileBase object to get access to the raw bytes of the uploaded file, its mime-type, and optionally save it to a database or disk.

    AJAX Improvements

    The ASP.NET MVC RC includes a number of AJAX enhancements:

    jQuery Intellisense Files included within ASP.NET MVC Project Template

    Newly created ASP.NET MVC projects now include both the standard jQuery library (both full and compressed versions), as well as the –vsdoc intellisense documentation file used by Visual Studio to provide richer intellisense support for it (you can learn more about this here):

    This enables rich jQuery JavaScript intellisense within client-script blocks and JavaScript files:

    Today’s RC build ships jQuery 1.2.6.  We are planning to ship the upcoming jQuery 1.3.1 release for the final ASP.NET MVC 1.0 release, and will include an updated JavaScript intellisense file for it. 

    Request.IsAjaxRequest Property

    The Request.IsAjaxRequest property can be used to detect whether a request is being sent from an AJAX call on the client (and is useful for scenarios where you want to gracefully degrade if AJAX is not enabled).  The logic within this method was updated with the RC to now recognize the “X-Requested-With” HTTP header (in addition to the form field sent by ASP.NET AJAX).  This is a well known header sent by JavaScript libraries such a Prototype, jQuery, and Dojo – and now enables a unified way to check for AJAX within an ASP.NET MVC request. 

    JavaScriptResult ActionResult and JavaScript() helper method

    The Controller base class now has a JavaScript() helper method that returns a new ActionResult class of type JavaScriptResult.  This supports the ability to return raw JavaScript that will then be executed on the client by the built-in ASP.NET MVC helper methods.  This can be useful for scenarios where you want to cause conditional JavaScript to execute on the client based on server logic.

    Summary

    We are pretty excited to be in the final “home stretch” of ASP.NET MVC V1.  Please report any issues you find with the RC build as soon as possible so that we can get them resolved for the final release.  The team plans to carefully monitor feedback over the next few weeks, and assuming no big issues come up ship the official V1 build next month.

    Hope this helps,

    Scott

  • ASP.NET MVC Design Gallery and Upcoming View Improvements with the ASP.NET MVC Release Candidate

    Today we launched a new ASP.NET MVC Design Gallery on the www.asp.net site.  The design gallery hosts free HTML design templates that you can download and easily use with your ASP.NET MVC applications.  Included with each design template is a Site.master file, a CSS stylesheet, and optionally a set of images, partials, and helper methods that support them. 

    The gallery allows you to preview each of the designs online, as well as download a .zip version of them that you can extract and integrate into your site.  The gallery allows anyone to create and submit new designs under the creative commons license.  Visitors to the gallery can vote to provide feedback on them (thumbs up/thumbs down).  The most popular designs show up at the top of the gallery. 

    We think this will provide a useful way for developers to more easily create attractive, standards compliant, sites.  It will also hopefully encourage folks to create and share designs that can be easily re-used by others.

    Upcoming View Improvements with the Release Candidate

    While on the topic of UI, I thought I'd also share a few details about some of the View-related improvements that are coming with the new ASP.NET MVC Release Candidate build that will be shipping shortly.  In addition to bug fixes, the RC incorporates a number of view-specific feature additions and community suggestions.

    Views without Code-Behind Files

    Based on feedback from a lot of people, we've decided to make a change so that MVC view files by default do not have code-behind files. This change helps to reinforce the purpose of views in a MVC world (which are intended to be purely about rendering and to not contain any non-rendering related code), and for most people eliminates unused files in the project:

    With the ASP.NET MVC Beta, developers could eliminate the code-behind file by using the CLR syntax for generic types in a view's inherits attribute, but that CLR syntax is (to put it mildly) pretty undiscoverable and hard to use.  The ASP.NET MVC team was able to combine a few extensibility features already in ASP.NET to now enable the standard VB/C# language syntax within the inherits attribute with the ASP.NET RC build:

    One other nice benefit of not using a code-behind file is that you'll now get immediate intellisense when you first add them to the project.  With the beta you had to do a build/compile immediately after creating a view in order to get code intellisense within it.  The RC makes the workflow of adding and immediately editing a view compile-free and much more seamless.

    Top-Level Model Property on Views

    With previous builds of ASP.NET MVC, you accessed the strongly typed model object passed to the view using the ViewData.Model property:

    The above syntax still works, although now there is also a top-level "Model" property on ViewPage that you can use:

    This property does the same thing as the previous code sample - its main benefit is that it allows you to write the code a little more concisely.

    HTML/AJAX Helpers Now Enable Expression Syntax

    One of the requests a few people have asked for is the ability to use strongly-typed expression syntax (instead of using strings) when referring to the Model when using a View's HTML and AJAX helper objects.

    With the beta build of ASP.NET MVC this wasn't possible, since the HtmlHelper and AjaxHelper helper classes didn't expose the model type in their signature, and so people had to build helper methods directly off of the ViewPage<TModel> base class in order to achieve this.  The ASP.NET MVC RC build introduces new HtmlHelper<TModel> and AjaxHelper<TModel> types that are exposed on the ViewPage<TModel> base class.  These types now allow anyone to build strongly-typed HTML and AJAX helper extensions that use expression syntax to refer to the View's model.

    For example, I could build a (very simple) strongly-typed "TextBox" helper method using the code below:

    And then use it within any of my views to bind against a Product model object like so:

    Visual Studio will provide full intellisense for the strongly-typed expression syntax when working against the View's model in the source editor in this way:

     

    Note: the HTML helper extensions in the core ASP.NET MVC V1 assembly will still use the existing (non-expression based) syntax.  We are then planning to add expression-based versions to the MVCFutures assembly. You can of course also add your own helper methods (using either strings or strongly-typed BLOCKED EXPRESSION.  All of the built-in helper methods can also optionally be removed (because they are extension methods) if you want to replace or override them with your own.

    Scaffolding Support

    The ASP.NET MVC RC build includes automatic "UI scaffolding" support when creating views using the new ASP.NET MVC "Add View" command inside Visual Studio.  The scaffolding support enables the automatic generation of views against any .NET type or object - meaning it can work against POCO classes, LINQ to SQL, LINQ to Entities, NHibernate, SubSonic, LLBLGen Pro, or any other object model. The scaffolding engine uses reflection to retrieve the public shape of a View's model type, and then passes it to a scaffolding template to populate appropriate markup based on it within the view being created.

    For example, assume we have a ProductsController class and want to create an "Edit" action on it to display an edit view of a particular Product.  Using the RC build we can right-click within our "Edit" action method and choose the "Add View" context menu command like so:

    Within the "Add View" dialog we can then indicate that we are passing a "Product" type to our View:

    We can indicate that we want an "Empty" view template created (like above), or indicate that we want VS to automatically scaffold a form "Edit" view for the Product object we are supplying:

    If we choose the "Edit" template VS will automatically generate a file for us that has the appropriate HTML and validation helpers to create an editable form view:

    We can then run the application and immediately get edit UI:

    We can then go in and change the generated edit.aspx file however we want to tweak/customize it. 

    One of the really nice things about the scaffolding system we are shipping is that it is implemented using Visual Studio's built-in T4 code generation system (Scott Hanselman has a nice post about this here).  The "List", "Edit", "Create" and "Details" templates we ship with ASP.NET MVC can all be completely customized or replaced with T4 templates of your own (or downloaded from the ASP.NET MVC Design Gallery). So if you have your own particular way of creating HTML, or want to use custom HTML helpers (for example: strongly-typed expression based ones) you can update the default templates and the scaffolding system will use them going forward. 

    We are planning to enable the templates to be overriden both on a machine-wide level, as well as on a per-project level (so that you can check-in application-specific scaffolding templates under source control and share them across a team).

    MSBuild Task for Compiling Views

    By default when you do a build on an ASP.NET MVC project it compiles all code within the project, except for the code within view files.  With the ASP.NET MVC Beta you had to roll your own MSBuild task if you wanted to compile the views.  The ASP.NET MVC RC build now includes a built-in MSBuild task that you can use to include views as part of the project compilation process.  This will verify the syntax and code included inline within all views and master pages for the application, and give you build errors if it encounters any problems.

    For performance reasons we don't recommend running this for quick compiles during development, but it is convenient to add to particular build configuration profiles (for example: staging and deployment) and/or for use with Build or CI (continuous integration) servers.

    Other ASP.NET MVC Release Candidate features coming

    Above is a short list of some of the view-specific functionality coming with the release candidate build. 

    There are many other features and requests coming with the RC as well including: IDataErrorInfo support to enable models to surface validation error messages, as well as richer error validation extensibility to enable you to use your own approach to surface model validation errors to ModelBinders (the IDataErrorInfo support is built on top of this); new FileResult and JavaScriptResult ActionResult types (allowing you to more easily download files as well as executable JavaScript to browsers); built-in jQuery -vsdoc intellisense support; refactored AccontController support to enable easier unit testing and extensibility with form login scenarios; a variety of project template improvements, more extensibility everywhere; lots of bug fixes; and a few other cool features I'll blog about later once the RC is out.

    We'll be releasing the ASP.NET MVC Release Candidate in January.  Our plan is to have that build be ASP.NET MVC V1 API and feature-complete and have zero known bugs.  We'll give people a short period to upgrade to it, give it a good tire-kicking, and report any last minute issues they find.  We'll then ship the official V1 release shortly after that (so not far off now).

    Hope this helps,

    Scott

More Posts Next page »

This Blog

Syndication

Powered by Community Server, by Telligent Systems
'