ASP. NET controls HTTP Cache

Source: Internet
Author: User

In the previous blog [describe ASP. NET Cache and its advanced usage,
I have introduced ASP. NET Cache, a Cache API used by the server. In the process of developing an ASP. NET Website, cache can be used in many places,
The reason is that ASP. NET is a server-based development platform. Naturally, we often use various caching technologies in server-side code,
However, because the WEB application serves the client browser, we generally cannot directly control browser behavior,
The browser can use some optimization methods to display the page more quickly according to the instructions of the background website.
The client browser also has its own caching mechanism. Generally, the browser also uses caching to optimize the page display process,
However, we cannot directly use the C # code to control the browser's cache operations, but we can tell the browser how to use the cache to optimize the website performance.

The topic of this blog is to use ASP. NET to control browser caching during HTTP requests.

Normal HTTP Request Process

Before introducing the HTTP request process of a browser, I think it is necessary to first look at the process of requesting a common ASPX page by the browser.
Note: This document describes the HTTP request process and uses Fiddler to analyze the specific request process in large quantities.

It is a request process for a common ASPX page. It is common because I did not perform any cache processing on the page after creating it.
The response status of the server is HTTP/1.1 200 OK, which indicates a successful response from the server.
In addition, pay attention to the Cache response header in the image. The reason why the red line is framed is to remind you that the content of this section will change in the following sections,
Pay attention to comparing them at that time. In fact, the result is only the default value. It does not indicate that the page needs to be cached.

Cache page request process

Next let's take a look at the request process of a cache page:

Compared with the previous image, we can see that we now have three response headers, max-age, Expires, and Last-Modified.

The meanings of these three headers are as follows:
1. max-age, Expires: the meaning to be expressed is almost the same. Max-age indicates how many seconds the HTTP response results should be cached.
Expires indicates when the response result of an HTTP request should be cached and expire, which is a UTC time.
Another Date header indicates the time when the HTPP response was sent. We can find that Date + max-age = Expires
2. Last-Modified: the server informs the client of the Last modification time of the HTTP document returned in this response. This header is related to the implementation of 304, which will be explained later.

After analyzing the HTTP request process, let's take a look at what the server page looks like:

<% @ Page Language = "C #" %> <% @ OutputCache Duration = "10" VaryByParam = "None" %> 

Note: The most critical line of code in the above Code is:

<%@ OutputCache Duration="10" VaryByParam="None" %>

The OutputCache command is used to output the above response headers, which is used to tell the browser that the page needs to be cached for 10 seconds.

At this point, some people may wonder: When will cache pages play a role?
To demonstrate the practical significance of the cache page, I will click these links on the page to explain the page display in the form of a series of requests,
And analyze the role of the cache based on the display results of the page.

Let's take a look at the display on this page:

The page is very simple, mainly displaying the page generation time and a Refresh link.
From the Page code provided above, we should know that if the page is generated by the server, the current time will be displayed.

However, when I keep clicking [refresh this page], the page time does not change. When I find that the time has changed, the page is displayed as follows:

During the test, I opened Fiddler all the time, and I also dropped the result of the request monitored by Fiddler:

From Fiddler, I saw that FireFox only had two requests, but I clicked the [refresh this page] for at least 10 times.

All of the above is a fact:If the page needs to jump to a cache page and the cache page has not expired, the browser does not initiate a request to the server, but uses the cache page.

Summary: The benefits of page caching are: Before the cache page expires, the userClick the jump LinkSubsequent access will not be requested again.
This can reduce the number of accesses to the server, so using this feature can improve program performance.

Server programming for cache pages

We have demonstrated the effect of the cache pages generated by using the OutputCache command. Since the commands need to be written to the page at the design stage of the page, they are not flexible enough,
It cannot be adjusted at runtime. Although ASP. NET also allows us to use CacheProfile to introduce the configuration defined in Web. config, the configuration is still not flexible in runtime code.
Let's take a look at how to use the code to achieve the above effect.

In fact, using code to implement cache pages is also very simple, just like this:

protected void Page_Load(object sender, EventArgs e){    Response.Cache.SetCacheability(HttpCacheability.Public);    Response.Cache.SetExpires(DateTime.Now.AddSeconds(10.0));}

In fact, the key is to call Response. Cache.
Note: Response. Cache and my previous article
[Describe ASP. NET Cache and its advanced usage] the Cache mentioned in the blog is not the same thing. The two are completely irrelevant.
Response. Cache provides: methods used to set the Cache-specific HTTP header and to control the ASP. NET page output Cache.

Let's talk about the sample code in the previous two paragraphs. Some may wonder if their final results will be consistent?

To answer this question, I think it is necessary to take a look at the final code running on the page using the OutputCache command.

In the temporary compilation directory of ASP. NET, I found a version of the previous file processed by ASP. NET:

Private static System. web. UI. outputCacheParameters @__ outputCacheSettings = null; public demow.aspx (){//........ delete some Cache-independent code if (global: ASP. demow.aspx. outputCacheSettings = null) {System. web. UI. outputCacheParameters outputCacheSettings; outputCacheSettings = new System. web. UI. outputCacheParameters (); outputCacheSettings. duration = 20; outputCacheSettings. varyByParam = null; global: ASP. demow.aspx. outputcachesetask= outputcachesetask;}} protected override void FrameworkInitialize () {base. frameworkInitialize ();//........ this. initOutputCache (global: ASP. demow.aspx. outputCacheSettings); this. request. validateInput ();}

We can see that the Page's settings for the OutputCache command will eventually call the Page class to define a method:

protected internal virtual void InitOutputCache(OutputCacheParameters cacheSettings)

That method is too long, and the final processing method is still calling this. Response. Cache. If you are interested, you can check the method yourself.
As for the reason why the parameter of this method is OutputCacheParameters, I think this is easy to understand: it is convenient to include all the parameters of the OutputCache command together.

Therefore, for this reason, we can also directly call some methods of Response. Cache in the code to achieve the same effect,
Because the code can adjust the cache policy according to various parameters at runtime, it is more flexible and can be simplified by inheriting the base class.

Note: If you use the OutputCache command and use it with the OutputCache Module, you can achieve the effect of 304.

What is a 304 response?

Through the previous example, we have seen the benefits of Caching: it can be reduced to server access, because the page can be displayed without accessing the server, which for the server,
This reduces access pressure.However, if you force refresh the browser, the browser ignores the cache page and directly initiates a request to the server.

That is to say, the cache page will be invalid when the user forces to refresh the browser.
However, we use the cache page because we want to tell the browser that the data will not change for a certain period of time, so we do not need to request the server again.
However, we cannot block user behavior. Due to the browser's re-access, our original idea of caching will fail. The final result is:
When the page is re-executed on the server, the generated HTML code is re-sent to the client. The result of this refresh may also be meaningless, because the data may not change at all,
Therefore, the page cannot be changed.

Let's take a simple example: the client needs to browse an image.
When a browser accesses an image for the first time, the browser certainly does not have any cache records. At this time, it accesses the server and the server returns the image content.
However, because an image may be referenced by multiple pages, the possibility of modification is very small.
Therefore, there is no need to read the image and return the image content for multiple requests from the same browser. This will not only affect performance but also waste bandwidth.
Therefore, when server software such as IIS accesses such static files, some tags will be output in the response header to inform the browser that the file can be cached.

Back to the above-mentioned [user forced refresh] Question, what will IIS do at this time? See:

Note: Besides the HTTP status code 304,No data is returned.

To impress you with the 304 response, I captured an image response result with a status code of 200:

Through the comparison of the two images, we can see it clearly:304 and 200 are not only numerical differences, but are there any returned results.

If no result is returned, how does the Browser display it?
Do you have such doubts?
In fact, do not worry, the browser will use its cached version to display. That is to say: no matter how powerful the user is, the server does not return results, but it can still be displayed normally.

Obviously, this effect is what we want.
If you use this method, the cache page mentioned above has been badly refreshed by users.
However, I would like to remind you that the webdev.webserver.exe self-contained in Visual Studio does not support 304 responses, so you should not try it out without any results.

How to program 304 responses

We have seen the effect of 304 responses. However, in ASP. NET, the program we developed is a dynamic page, not an image,
We hope that a page can be cached for a period of time in this way. I think this requirement may be more meaningful.

Next, I will demonstrate how to implement it through programming.
In the following example, the page displays the time generated by the page on the server. The time has changed, indicating that the page has been re-executed.

I think it doesn't make much sense to intercept a series of images. I just took a picture and showed it many times.

It reflects the process of multiple requests to An ASPX page. It can be seen from the image that only the first response is 200, followed by 304, which is the expected result.

Let's take a look at its implementation code:

Public partial class Demo304: System. web. UI. page {protected void Page_Load (object sender, EventArgs e) {DateTime dt; if (DateTime. tryParse (Request. headers ["If-Modified-Since"], out dt) {// Note: If it is within 20 seconds, I will respond in 304. If (DateTime. now-dt ). totalSeconds <20.0) {Response. status Code = 304; Response. end (); return ;}}// note this call. It can generate the "Last-Modified" response header. After the browser receives this header, // when you access this page in the future, the time will be sent to the server in the form of "If-Modified-Since" //, so that the above Code can take effect. Response. Cache. SetLastModified (DateTime. Now );}}

Although the Code is not complex, I plan to explain it as follows:
When the browser requests the page for the first time, it will execute the SetLastModified call, which will output a "Last-Modified" Response Header in response,
Then, when the browser visits this page againContent,
The Request Header "If-Modified-Since" is sent to the server. In this case, the server can determine whether to use the 304 response based on the specific logic.

In the previous request image example, the server sends the Last modification time of the image file to the browser as "Last-Modified,
When the browser subsequently requests the image, the server is notified in the form of "If-Modified-Since, at this time, the server only needs to check this image again to see if the image has been modified since the last visit,
If no modification is made, of course, the browser will be notified in the form of 304: continue to use the Cache version.

In fact, the server also uses another pair of [Request/Response] headers:

The use of these two headers is: the server Outputs An ETag header. After receiving the header, the browser sends it to the server in the form of If-None-Match in subsequent requests,
For the server to determine whether to use the 304 response.

"Last-Modified" and "ETag" are both. In fact, you only need to use one of them. The key is to check how the server processes them. The browser only sends them again after receiving them.

However, the preceding sample code does not use a cache header. In fact, you can also use it to minimize access to the server. After all, the user will not always be able to use a browser.
Although there are big differences between the two methods, they can definitely complement each other.

In order to visually depict the request process of cache pages (or other documents), I drew a picture for your reference:

How to avoid HTTP caching

The previous section describes two methods to use browser cache. However, sometimes the browser may wish to discard the cached results.
Currently, browsers have cache functions, especially for some static files, such as images, JS, CSS, and HTML files.
But sometimes we need to update CSS and JS files. If the browser still uses its cached version, it will obviously be a problem.
In addition, some websites use URL rewriting to convert the original dynamic page extension to static HTML files,
Therefore, we still hope that the browser will not cache these pseudo static pages in some cases.

At this point, we want the browser to discard the results obtained from the HTTP request.
Generally, when a browser processes (as it thinks) static files, it will save the cached results according to the URL as the kEY,
Therefore, the general solution is to modify the URL. For example, if abc. js was originally requested, it should be changed to abc. js? T = 23434, followed by a parameter,
Make the previous cache ineffective. The value of parameter t can be manually specified based on the last modification time of the file. In short, you only need to change it.

However, for pseudo-static pages, we can no longer use this method, so there is no need to explain the reason.
Therefore, you can output a response header on the server to notify the browser of the Response Header. Do not cache this file.
For example, you can call this method:

Response.Cache.SetNoStore();

It will generate such response header content:

Cache-Control: private, no-store

Many browsers can recognize it. Another way is to set an expiration time.

The method of adding additional parameters in the URL mentioned above is also common in JS. For example, JQuery supports making an Ajax request not cached,
The method is to set {cache: false}. In the end, it adds a temporary parameter to the generated URL to ensure that the address of the subsequent request is not repeated,
This eventually avoids caching. JQuery is too simple to use, so I will not provide the sample code.

Click here to download the sample code

If you believe that reading this blog has some benefits, click 【Recommendation] Button.
If you want to discover my new blog more easily, click 【Follow Fish Li].
Because my enthusiasm for writing is inseparable from your support.

Thank you for reading this article. If you are interested in the content of my blog, please continue to follow up on my blog. I am Fish Li.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.