Bu makalenin Türkçe versiyonunu görmek için Tıklayınız.
In this article I will try to explain Custom Output Caching. Before diving into this subject let's remember the Output Caching in a short manner.
Output Caching - Partial Output Caching
In Asp.Net we use Output directive to cache our pages or some portion of the page. By using this directive in a page, we make all the page to be cached. And if we want to cache only a portion of the page we should seperate that portion as a usercontrol and put the Output directive in it. I will not explain the details of the output directive anymore. In the following Sample1 and Sample2 let's see some simple usages of it
Sample 1
In order to see the caching with naked eyes the samples are prepared to show the time-clock of the server on the page.
Html-ascx :
Codebehind :
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load spnTime.InnerText = Now.ToLongTimeString End Sub
In Sample 1, we created a usercontrol, showing the server time, and using this control in a page. As you see above, the usercontrol is cached for a period of 3 seconds, therefore it does not matter how frequently you requested the, the time seen on the page will change after 3 seconds.
Attention: In the above sample we have seen the usage of Output directive in aspx file of the page. We can also gain the same functionality in the codebehind by using the PartialCaching attribute. You can see it in Sample 2. The most of the parameters of the Output directive are also available for PartialCaching attribute, which are Duration, VaryByParams, VaryByControls, sqlDependency, Shared.
Sample 2
Html-ascx :
Codebehind :
_ Partial Public Class ClockForMethod2 Inherits System.Web.UI.UserControl Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load spnTime.InnerText = Now.ToLongTimeString End Sub End Class
Custom Output Caching
Although I name it as Custom Output Caching, in fact it is not exactly caching of a web page. Because a page or a usercontrol that is cached in the previous requests is not executed on the server. I mean the life-cycle of the control(page or usercontrol) does not start. While debugging the page does not break into Page_Load or other methods. Beacuse the page or usercontrol is loaded from the cached html of it. Oppositely, in the following sample, that I have called as Custom Output Caching, the page is executed normally, but we will interfere to simulate caching.
Output Caching is the caching of the output of a page and that output is the rendered Html of the page. So, we can do this manuallay. To achieve this, we should get the rendered html of the usercontrol that we wanted to be cached and save it in some store such as sessionstate, applicationstate, viewstate ya da cache. For the following requests after the caching we block the page to be executed and output the saved html.
Now let's see this method in action.
Sample 3
Html-ascx:
Codebehind :
Partial Public Class ClockForMethod3 Inherits System.Web.UI.UserControl Public ReadOnly Property isCached() As Boolean Get Return (HttpContext.Current.Cache.Get(Me.ClientID) Is Nothing = False AndAlso String.IsNullOrEmpty(HttpContext.Current.Cache.Get(Me.ClientID).ToString) = False) End Get End Property Public Property myCacheDuration() As TimeSpan Get Dim dur As TimeSpan = Me.ViewState("myCacheDuration") If dur = Nothing Then Return New TimeSpan(0, 0, 13) Else Return dur End If End Get Set(ByVal value As TimeSpan) Me.ViewState("myCacheDuration") = value End Set End Property Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load If isCached = False Then spnTime.InnerText = Now.ToLongTimeString End If End Sub Protected Overrides Sub Render(ByVal writer As System.Web.UI.HtmlTextWriter) Dim myCachedHtml As String = String.Empty If HttpContext.Current.Cache.Get(Me.ClientID) Is Nothing = False Then myCachedHtml = HttpContext.Current.Cache.Get(Me.ClientID).ToString End If If String.IsNullOrEmpty(myCachedHtml) = False Then writer.Write(myCachedHtml) Else Dim sb As New Text.StringBuilder Dim tw As New IO.StringWriter(sb) Dim hw As New HtmlTextWriter(tw) MyBase.Render(hw) HttpContext.Current.Cache.Insert(Me.ClientID, sb.ToString(), Nothing, Now.Add(myCacheDuration), Web.Caching.Cache.NoSlidingExpiration, Caching.CacheItemPriority.Normal, Nothing) writer.Write(sb.ToString()) End If End Sub End Class
Result
To say the truth the normal Output Caching method has more performance, flexibility and simple usage etc than the custom Output Caching. But it can be useful in some situations that you need special things to do in caching logic, because you have the full control.
You can see the samples given in this article in the attached file.
PartialCachingSite.zip (46,58 kb)