In this chapter, we will be focusing on one of the most common ASP.NET techniques like Caching to improve the performance of the application. Caching means to store something in memory that is being used frequently to provide better performance. We will see how you can dramatically improve the performance of an ASP.NET MVC application by taking advantage of the output cache.
In ASP.NET MVC, there is an OutputCache filter attribute that you can apply and this is the same concept as output caching in web forms. The output cache enables you to cache the content returned by a controller action.
Output caching basically allows you to store the output of a particular controller in the memory. Hence, any future request coming for the same action in that controller will be returned from the cached result. That way, the same content does not need to be generated each and every time the same controller action is invoked.
We need caching in many different scenarios to improve the performance of an application. For example, you have an ASP.NET MVC application, which displays a list employees. Now when these records are retrieved from the database by executing a database query each and every time a user invokes the controller action it returns the Index view.
Hence you can take advantage of the output cache to avoid executing a database query every time a user invokes the same controller action. In this case, the view will be retrieved from the cache instead of being regenerated from the controller action.
Caching enables you to avoid performing redundant work on the server.
Let’s take a look at a simple example of caching in our project.
[OutputCache(Duration = 60)] public ActionResult Index(){ var employees = from e in db.Employees orderby e.ID select e; return View(employees); }
As you can see, we have added “OutputCache” attribute on the index action of the EmployeeController. Now to understand this concept, let us run this application in debugger mode and also insert a breakpoint in the Index action method.
Specify the following URL http://localhost:63004/employee, and press ‘Enter’. You will see that the breakpoint is hit in the Index action method.
Press ‘F5’ button to continue and you will see the list of employees on your view, which are retrieved from the database.
Refresh the browser again within 60 seconds and you will see that the breakpoint is not hit this time. This is because we have used output cache with duration of seconds. So it will cache this result for 60 seconds and when you refresh the browser, it will get the result from the cache, and it won’t load the content from the database server.
In addition to duration parameter, there are other settings options as well which you can use with output cache. These settings are not only for MVC framework but it is inherited from ASP.Net Caching.
In some cases, you might want different cached versions, such as, when you create a detail page, then when you click on the detailed link you will get details for the selected employee.
But first we need to create the detail view. For this, right-click on the Details action method from the EmployeeController and select Add View…
You will see the Details name is selected by default. Now select Details from the Template dropdown and Employee from the Model class dropdown.
Click ‘Add’ to continue and you will see the Details.cshtml.
@model MVCSimpleApp.Models.Employee @{ Layout = null; } <!DOCTYPE html> <html> <head> <meta name = "viewport" content = "width = device-width" /> <title>Details</title> </head> <body> <div> <h4>Employee</h4> <hr /> <dl class = "dl-horizontal"> <dt> @Html.DisplayNameFor(model => model.Name) </dt> <dd> @Html.DisplayFor(model => model.Name) </dd> <dt> @Html.DisplayNameFor(model => model.JoiningDate) </dt> <dd> @Html.DisplayFor(model => model.JoiningDate) </dd> <dt> @Html.DisplayNameFor(model => model.Age) </dt> <dd> @Html.DisplayFor(model => model.Age) </dd> </dl> </div> <p> @Html.ActionLink("Edit", "Edit", new { id = Model.ID }) | @Html.ActionLink("Back to List", "Index") </p> </body> </html>
You can take advantage of the VaryByParam property of the [OutputCache] attribute. This property enables you to create different cached versions of the very same content when a form parameter or query string parameter varies. Following is the implementation of Details action.
// GET: Employee/Details/5 [OutputCache(Duration = int.MaxValue, VaryByParam = "id")] public ActionResult Details(int id){ var employee = db.Employees.SingleOrDefault(e => e.ID == id); return View(employee); }
When the above code is compiled and executed, you will receive the following output by specifying the URL http://localhost:63004/employee.
Click on the Details link of any link and you will see the details view of that particular employee.
The Details() action includes a VaryByParam property with the value “Id”. When different values of the Id parameter are passed to the controller action, different cached versions of the Details view are generated.
It is important to understand that using the VaryByParam property results in more caching. A different cached version of the Details view is created for each different version of the Id parameter.
You can create a cache profile in the web.config file. It is an alternative to configuring output cache properties by modifying properties of the [OutputCache] attribute. It offers a couple of important advantages which are as follows.
Controls how controller actions cache content in one central location.
Creates one cache profile and apply the profile to several controllers or controller actions.
Modifies the web configuration file without recompiling your application.
Disables caching for an application that has already been deployed to production.
Let’s take a look at a simple example of cache profile by creating the cache profile in web.config file. The <caching> section must appear within the <system.web> section.
<caching> <outputCacheSettings> <outputCacheProfiles> <add name = "Cache10Min" duration = "600" varyByParam = "none"/> </outputCacheProfiles> </outputCacheSettings> </caching>
You can apply the Cache10Min profile to a controller action with the [OutputCache] attribute which is as follows.
[OutputCache(CacheProfile = "Cache10Min")] public ActionResult Index(){ var employees = from e in db.Employees orderby e.ID select e; return View(employees); }
Run this application and specify the following URL http://localhost:63004/employee
If you invoke the Index() action as shown above then the same time will be returned for 10 Min.