Dotnet 3.5 interview questions and answers Headline Animator

Thursday, September 16, 2010

ASP.NET MVC HandleError Attribute, Custom Error Pages and Logging Exceptions

I'm sure I don't need to tell you how bad serving a Yellow Screen of Death to your users is. Nonetheless, it seems to be pretty common practice across the web. One of the first things I do when setting up a new ASP.NET project is set up custom error pages and ensure all exceptions are logged (who wants to find out about their errors from their clients?). Since things work slightly differently in ASP.NET MVC I thought I'd dig in and find the best way to do the same thing.

The HandleError Attribute
The HandleError attribute (which appears on the default controllers in an MVC project) tells the framework that if an unhandled exception occurs in your controller that rather than showing the default Yellow Screen of Death it should instead serve up a view called Error. The controller-specific View folder will be checked first (eg. Views/Home/Error.aspx) and if it's not found, the Shared folder (Views/Home/Error.aspx) will be used.

But How Do I Log Exceptions?
You might've spotted the problem with HandleError. It just outputs a view, and doesn't let you run any code. This might be fine if you don't want users to see errors but don't really care for fixing them. Hopefully you think this isn't acceptable and you want to investigate all exceptions!

The OnException Method
The System.Web.Mvc.Controller class contains a method called OnException which is called whenever an exception occuts within an action. This does not rely on the HandleError attribute being set. If you're being a good coder and have your own base Controller class you can override this method in one place to handle/log all errors for your site. You might choose to send emails and/or detect duplicate exceptions and discard them. For now, I'm just going to write them all to a text file in my App_Data folder.

protected override void OnException(ExceptionContext filterContext)
{
WriteLog(Settings.LogErrorFile, filterContext.Exception.ToString());
}

///
/// Logs a message to the given log file
///

///
The filename to log to///
The message to logstatic void WriteLog(string logFile, string text)
{
//TODO: Format nicer
StringBuilder message = new StringBuilder();
message.AppendLine(DateTime.Now.ToString());
message.AppendLine(text);
message.AppendLine("===========================");
System.IO.File.AppendAllText(logFile, message.ToString());
}

This works great, but it still shows our user an unhandled exception message, even if we use the HandleError attribute. This makes the HandleError attribute look rather useless, so I've removed it. We can easily show the friendly error ourselves with the following code:

filterContext.ExceptionHandled = true;
this.View("Error").ExecuteResult(this.ControllerContext);

It's important to set ExceptionHandled to true, otherwise you'll still see the default unhandled exception message. The OnException method returns void so we must Execute the view and pass in the ControllerContext ourselves.

How Do I see my own Errors During Development?
It's a little inconvenient to open log files or keep commenting out your error handling code while developing to see exceptions and stack traces. You might remember ASP.NET has a nice web.config setting that configures custom errors. This property is exposed via MVC, so we can set up our config to show friendly errors to remote users only:

<customErrors mode="RemoteOnly" />

Then all we need to do in our OnException method is check this value and serve up the custom error view only if it returns true.

protected override void OnException(ExceptionContext filterContext)
{
WriteLog(Settings.LogErrorFile, filterContext.Exception.ToString());

// Output a nice error page
if (filterContext.HttpContext.IsCustomErrorEnabled)
{
filterContext.ExceptionHandled = true;
this.View("Error").ExecuteResult(this.ControllerContext);
}
}


It's worth noting that IsCustomErrorEnabled will resolve the RemoteOnly option for you, you don't need to check where the user is coming from. Now out site serves up friendly errors to users and logs all exceptions without us losing the ability to see stack traces during development.

Monday, October 26, 2009

ASP.NET MVC Best Practices


ASP.NET MVC Best Practices



Wednesday, October 7, 2009

Model View Controller (MVC) Architecture in ASP.NET

This article will enhance your vision on the usage of Robustness Analysis in conjunction with Model View Controller, using UML with application in ASP.NET.

http://www.codeproject.com/aspnet/ModelViewController.asp

Thursday, September 24, 2009

MVC AJAX Form with Ajax.BeginForm() and jQuery Thickbox ...


A relatively common scenario you might want in your application is the ability for a user to click a link that pops up a little dialog to submit some information.  For example, let’s say you have this form where the user could click the “Contact this person” link:








After clicking this link, it pops up the following dialog where the user can type in their message:











This scenario can be implemented with MVC with very few lines of code.  First off, we’ll be using the AJAX HTML Message pattern so that the AJAX messages that are going across the wire are simple HTML snippets.  Also, we’ll use jQuery Thickbox for our dialog. The first thing we need to do it to implement our “Contact this person” link:
   1:  <%=Html.ActionLink("Contact this person", "Index", "Contact", new { height = 200, width = 300 }, new { @class = "thickbox" }) %>
This is a pretty typical implementation of the jQuery thickbox.  We’re specifying that we want an AJAX call to be made to our ContactController.Index() method. The HTML that this ActionLink renders will simply look like this:
   1:  <a class="thickbox" href="/Contact?height=200&amp;width=300">Contact this person</a>
The complete code for the ContractController looks like this:
   1:  public class ContactController : Controller
   2:  {
   3:      public ActionResult Index()
   4:      {
   5:          return View(new ContactMessage());
   6:      }
   7:  
   8:      [ActionName("Index")]
   9:      [AcceptVerbs(HttpVerbs.Post)]
  10:      public ActionResult SubmitMessage(ContactMessage message)
  11:      {
  12:          return this.View("Confirmation", message);
  13:      }
  14:  }
It is important to note that both views returned by the ContactController’s action methods are both partial views (i.e., Index.ascx and Confirmation.ascx) with our HTML snippets in there. We know that in the Index.ascx we want to do an AJAX form submission/post rather than a full page form submission. There are a couple of ways to do this including using the jQuery Form plugin. However, in this case, the MVC framework already comes built-in with this functionality so we don’t have to rely on the jQuery Form plugin (unless we want to). Most of the time we find ourselves using the Html property of the View which is of type HtmlHelper.  However, there is also an Ajax property of the view of type AjaxHelper. The AjaxHelper has a BeginForm method that will allow you to submit the form via AJAX. You’ll need to make sure you include the MicrosoftAjax.js and MicrosoftMvcAjax.js scripts in your page to use the Ajax helpers.  The complete implementation for the Index.ascx can just look like this:
   1:  <%@ Control Language="C#" Inherits="System.Web.Mvc.ViewUserControl<MvcAjaxForm.Models.ContactMessage>" %>
   2:  
   3:  <h2>Contact</h2>
   4:     
   5:  <% using (Ajax.BeginForm("Index", "Contact", new AjaxOptions { UpdateTargetId = "contactArea" } )) { %>
   6:      <div id="contactArea">
   7:          Email Address: <%=Html.TextBox("EmailAddress") %> <br /><br />
   8:          Message: <%=Html.TextArea("MessageText")%>
   9:          <input type="submit" />
  10:      </div>
  11:  <% } %>
Notice the UpdateTargetId is specifying the “contactArea” div.  This causes all HTML that is sent back on the form post (i.e., the confirmation message) to be displayed inside this div only. 

 Original Source:
http://geekswithblogs.net/michelotti/archive/2009/08/31/mvc-ajax-form-with-ajax.beginform-and-jquery-thickbox.aspx

Tuesday, September 22, 2009

ASP.NET MVC jQuery Autocomplete plug-in using JSON.

ASP.NET MVC jQuery Autocomplete plug-in using JSON.

This post demonstrate how to use JQuery Autocomplete feature in ASP.NET MVC. In this demo we call the controller Action method to get the data in JSON format and bind it to the text box to accomplish the Autocomplete feature.

Before starting download the js and css file from jQuery Autocomplete plugin and add in the project and follow the steps mention below

Step 1. Add the following code for action method in controller

public
ActionResult StateLookup(string q, int limit)

{


var jsonData = new[]{


new {Code = "AL", Name = "Alabama"},


new {Code = "CA", Name= "Califonia"},


new {Code = "IN", Name = "Indiana"},


new {Code = "MD", Name = "Maryland"},


new {Code = "NJ", Name = "New Jersey"}


 


 

};


return Json(jsonData);

}

I have used hardcode JSON list for the state. You can construct the JSON data from database using LINQ.

Step 2. Add the following java script in the view

<script
type="text/javascript">

$(document).ready( function() {

$('#state').autocomplete('<%=Url.Action("StateLookup", "Home") %>', {

dataType: 'json',

parse: function(data) {


var rows = new Array();


for(var i=0; i<data.length; i++){

rows[i] = { data:data[i], value:data[i].Code, result:data[i].Code };

}


return rows;

},

formatItem: function(row, i, n) {


return row.Code + ' - ' + row.Name;

},

width: 300,

mustMatch: true,

});

});

</script>

Here, I specify that the rows in the drop down will have the state "Code - Name" format, and that the value that will be put in the textbox is the Code property of the selected item. This is done with the value property of the rows array.

Step 2. Add the HTML Text box

<%= Html.TextBox("state")%>

Complie the application and run it. To get this running, don't forget to include the required javascript files and the css to style the autocomplete drop down.

Wednesday, September 9, 2009

How to use textbox

HTML Helper for TextBox will be rendered as input elements in HTML. Check the below code.

  1. <!--HTML helper method for TextBox with ID only -->  
  2. <%= Html.TextBox("txtFirstName") %>  
  3. <input id="txtFirstName" name="txtFirstName" type="text" value="" />  
  4.   
  5. <!--HTML helper method for TextBox with ID and Value -->  
  6. <%= Html.TextBox("txtFirstName","Alice") %>  
  7. <input id="txtFirstName" name="txtFirstName" type="text" value="Alice" />  
  8.   
  9. <!--HTML helper method for TextBox with ID and Value and custom attributes. use '@' if the attribute name is keyword in C# or VB -->  
  10. <%= Html.TextBox("txtFirstName", "Alice", new { @class="error"client_selector="alphanumeric" })%>  
  11. <input class="error" client_selector="alphanumeric" id="txtFirstName" name="txtFirstName" type="text" value="Alice" />