Combining JQuery Form Validation and Ajax Submission with ASP.NET

As I mentioned before, I’m really excited that we’re shipping jQuery with ASP.NET MVC and with Visual Studio moving forward. Just recently, we issued a patch that enables jQuery Intellisense to work in Visual Studio 2008.

But if you’re new to jQuery, you might sit down at your desk ready to take on the web with your knew found JavaScript light saber, only to stare blankly at an empty screen asking yourself, “Is this it?”

See, as exciting and cool as jQuery is, it’s really the vast array of plugins that really give jQuery its star power. Today I wanted to play around with integrating two jQuery plugins – the jQuery Form Plugin used to submit forms asynchronously and the jQuery Validation plugin used to validate input.

Since this is a prototype for something I might patch into Subtext, which still targets ASP.NET 2.0, I used Web Forms for the demo, though what I do here easily applies to ASP.NET MVC.

Here are some screenshots of it in action. When I click the submit button, it validates all the fields. The email field is validated after the input loses focus.

validation

When I correct the data and click “Send Comment”, it will asynchronously display the posted comment.

async-comment-response

Let’s look at the code to make this happen. Here’s the relevant HTML markup in my Default.aspx page:

<div id="comments" ></div>

<form id="form1" runat="server">
<div id="comment-form">
  <p>
    <asp:Label AssociatedControlID="title" runat="server" Text="Title: " />
    <asp:TextBox ID="title" runat="server" CssClass="required" />
  </p>
  <p>
    <asp:Label AssociatedControlID="email" runat="server" Text="Email: " />
    <asp:TextBox ID="email" runat="server" CssClass="required email" />
  </p>
  <p>
    <asp:Label AssociatedControlID="body" runat="server" Text="Body: " />
    <asp:TextBox ID="body" runat="server" CssClass="required" />
  </p>
  <input type="hidden" name="<%= submitButton.ClientID %>" 
    value="Send Comment" />
  <asp:Button runat="server" ID="submitButton" 
    OnClick="OnFormSubmit" Text="Send Comment" />
</div>
</form>

I’ve called out a few important details in code. The top DIV is where I will put the response of the AJAX form post. The CSS classes on the elements provide validation meta-data to the Validation plugin. What the heck is that hidden input doing there?

Notice that hidden input that duplicates the field name of the submit button. That’s the ugly hack part I did. The jQuery Form plugin doesn’t actually submit the value of the input button. I needed that to be submitted in order for the code behind to work. When you click on the submit button, a method named OnFormSubmit gets called in the code behind.

Let’s take a quick look at that method in the code behind.

protected void OnFormSubmit(object sender, EventArgs e) {
    var control = Page.LoadControl("~/CommentResponse.ascx") 
        as CommentResponse;
    control.Title = title.Text;
    control.Email = email.Text;
    control.Body = body.Text;

    var htmlWriter = new HtmlTextWriter(Response.Output);
    control.RenderControl(htmlWriter);
    Response.End();
}

Notice here that I’m just instantiating a user control, setting some properties of the control, and then rendering it to the output stream. I’m able to access the values in the submitted form by accessing the ASP.NET controls.

This is sort of like the Web Forms equivalent of ASP.NET MVC’s partial rendering ala the return PartialView() method. Here’s the code for that user control.

<%@ Control Language="C#" CodeBehind="CommentResponse.ascx.cs" 
    Inherits="WebFormValidationDemo.CommentResponse" %>
<div style="color: blue; border: solid 1px brown;">
    <p>
        Thanks for the comment! This is what you wrote.
    </p>
    <p>
        <label>Title:</label> <%= Title %>
    </p>
    <p>
        <label>Email:</label> <%= Email %>
    </p>
    
    <p>
        <label>Body:</label> <%= Body %>
    </p>
</div>

Along with its code behind.

public partial class CommentResponse : System.Web.UI.UserControl {
    public string Title { get; set; }
    public string Email { get; set; }
    public string Body { get; set; }
}

Finally, let’s look at the script in the head section that ties this all together and makes it work.

<script src="scripts/jquery-1.2.6.min.js" type="text/javascript"></script>
<script src="scripts/jquery.validate.js" type="text/javascript"></script>
<script src="scripts/jquery.form.js" type="text/javascript"></script>
<% if (false) { %>
<script src="scripts/jquery-1.2.6-vsdoc.js" type="text/javascript"></script>
<% } %>
<script type="text/javascript">
    $(document).ready(function() {
        $("#<%= form1.ClientID %>").validate({
            submitHandler: function(form) {
                jQuery(form).ajaxSubmit({
                    target: "#comments"
                });
            }
        });
    });
</script>

The if(false) section is for the jQuery intellisense, which only matters to me at design time, not runtime.

What we’re doing here is getting a reference to the form and calling the validate method on it. This sets up the form for validation based on validation meta data stored in the CSS classes for the form inputs. It’s possible to do this completely external, but one nice thing about this approach is now you can style the fields based on their validation attributes.

We then register the ajaxSubmit method of the jQuery Form plugin as the submit handler for the form. So when the form is valid, it will use the ajaxSubmit method to post the form, which posts it asynchronously. In the arguments to that method, I specify the #comments selector as the target of the form. So the response from the form submission gets put in there.

As I mentioned before, the hidden input just ensures that ASP.NET runs its lifecycle in response to the form post so I can handle the response in the button’s event handler. In ASP.NET MVC, you’d just point this to an action method instead and not worry about adding the hidden input.

In any case, play around with these two plugins as they provide way more rich functionality than what I covered here.

What others have said

Requesting Gravatar... Kirk Clawson Nov 21, 2008 4:30 PM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
The link to the validation plugin is pointing to the Form plugin. :)
Requesting Gravatar... haacked Nov 21, 2008 5:37 PM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
@Kirk. Fixed! Thanks!
Requesting Gravatar... Ajay Nov 21, 2008 9:47 PM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
Phil,

Can we see some ASP.Net MVC samples with inbuilt Ajax helpers and jQuery combined. Its long pending, I guess.

ASP.Net MVC Rocks!!! Keep up the good work.

Thanks.
Requesting Gravatar... Thomas Hansen Nov 22, 2008 3:26 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
I think form input retrieval like these are a gazillion times easier to implement using something like Ra-Ajax ( http://ra-ajax.org )
Requesting Gravatar... rtpHarry Nov 22, 2008 3:37 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
Does this mean that I should be moving away from using the built in asp.net validator controls in future?
Requesting Gravatar... Kyle Baley Nov 22, 2008 4:35 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
I can see this being useful to convert existing web pages to use AJAX form submission. But what are your thoughts on using this method vs. collecting the data you need and using $.ajax or $.post to send it to, say, an MVC action? I've been doing the latter because if feels more task-based. You collect the data you need, call a URL, and handle the callback all for a specific task, not an entire form. Plus then you don't actually need a form.
Requesting Gravatar... Matt Hinze Nov 22, 2008 5:29 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
This doesn't really apply to most ajax scenarios. Why not just go the normal, non-ajax way with this form? You need validation (and server side) PLUS modals plus multiple forms and success and failure json wrappers to your response html.
Requesting Gravatar... Steve Nov 22, 2008 6:29 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
Thanks Phil.

I've been using the jquery form plugin with validators and it's worked well.

Other worthwhile plugin's to explore:
jquery mask
jquery jqmodal - great for modal dialogs (http://dev.iceburg.net/jquery/jqModal/)
jquery blockUI

Now, what I've done personally is wrap this functionality up into Html helpers.

ie.
Html.Dialog()

Additionally, adding 'ajax' validation support like above, I attach helpers to the normal forms (rather than create a separate 'ajax form helper'). That part is nice because it's easy to encapsulate all the validation scripts, etc... in the helpers.

Glad to see jquery get some press - it's an incredible library - good support from the community - and truly 'unobtrusive'.

I think MS should create a jquery plugin to do the ms ajax 'proxy' scripting - it's the one part of the ms ajax library that I like.

Even better - ask Nikhil Kothari to include it in his Script# :)
Requesting Gravatar... Josh Nov 22, 2008 9:24 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
I have been using the JQuery validation library since MVC Preview 4, and with great success. Adding in a few other JQuery libraries to your arsenal, you have the ability to really create some user friendly forms.
Requesting Gravatar... Justice~! Nov 22, 2008 11:22 PM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
@Ajay - tune in this coming week or two as I'll be talking about examples more than likely, or E-mail me and then I'll tell you.

@Kyle - funny you should mention this!
Requesting Gravatar... Gabriel Bogéa Nov 23, 2008 5:38 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
Hi Phil, I've been doing tests along these lines lately. I know you just wanted to demonstrate the plugins but I've been seeing a lot of people using jQuery to submit their forms instead of using the MVC Ajax.BeginFom helper. I usually prefer to use the helper methods when they are available instead of using jQuery.
Is the jQuery form submit just another option or is the MVC team leaning towards leaving the ajax to jQuery and not focusing so much on the MVC ajax helpers?
Requesting Gravatar... Shiju Varghese Nov 23, 2008 5:18 PM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
I did the blog post Ajax and Validations using jQuery with ASP.NET MVC Preview 5. Check weblogs.asp.net/.../...lidations-using-jquery.aspx
Requesting Gravatar... Josh Dec 18, 2008 12:02 PM
# Are you sure?
Are you sure about this line:
var control = Page.LoadControl("~/CommentResponse.ascx")
as CommentResponse;

it looks like a vb to me. and it does not compile, of course. ('var' could not be found..."

Thanks.

Requesting Gravatar... haacked Dec 18, 2008 12:57 PM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
@Josh are you using ASP.NET 3.5? You can replace "var" with CommentResponse if not.
Requesting Gravatar... Naveed Feb 19, 2009 4:07 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
Thanks, its nice
Requesting Gravatar... Tommy Mar 31, 2009 6:24 AM
# re: Combining JQuery Form Validation and Ajax Submission with ASP.NET
Didn't get this to work with a page using a masterpage. I added a breakpoint in the OnFormSubmit event in default.aspx.cs, and it steps in there only the second time the form is submitted. The first time, the entire page is (re-)loaded in the comments-div.

Crap, this is why I stayed with MVC, instead of strugling with webforms... :-(

What do you have to say?

(will show your gravatar)
Please add 3 and 4 and type the answer here: