You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

ASP.NET 如何通过ETag实现缩略图缓存 避免页面加载刷新重复请求

解决方案

第一步:修正现有缓存配置冲突

你现有代码存在两处缓存规则冲突,需要先调整:

  • 同时设置了SetCacheability(HttpCacheability.Public)和Response.CacheControl = "private",二者优先级后者更高,建议删除context.Response.CacheControl = "private"这行,保留Public允许CDN/代理缓存缩略图,降低源站压力。
  • 同时设置了Expires为1年、MaxAge为1小时,HTTP规范中MaxAge优先级高于Expires,如果你希望图片长期缓存,将SetMaxAge改为context.Response.Cache.SetMaxAge(new TimeSpan(365, 0, 0, 0));即可。

第二步:添加ETag校验逻辑

校验逻辑要放在请求处理逻辑的最开头,无需读取文件即可返回304,最大化提升性能,完整实现代码如下:

// 优先校验ETag,放在所有逻辑最前面
string currentETag = "";
// 注意:你的ETag是从文件名生成,文件名不变的话可以直接根据fileUri拼接生成ETag,不需要先FetchFile
// 这里演示和你现有生成逻辑保持一致的写法,建议可以优化为不读文件直接生成ETag
var uriFetcher = new UriFetcher(fileUri);
var tempPath = uriFetcher.FetchFile();
currentETag = "\"" + tempPath.Split('\\').Last() + "\"";

// 获取请求头的If-None-Match
var requestedETag = context.Request.Headers["If-None-Match"];
// 比对ETag,匹配直接返回304
if (!string.IsNullOrEmpty(requestedETag) && requestedETag.Trim() == currentETag)
{
    context.Response.StatusCode = (int)HttpStatusCode.NotModified;
    context.Response.SuppressContent = true;
    return;
}

// 以下是原有逻辑,不需要修改
var mime = MimeType(tempPath);

context.Response.Cache.SetCacheability(HttpCacheability.Public);
context.Response.Cache.SetLastModified(DateTime.Now);
context.Response.Cache.SetValidUntilExpires(true);
context.Response.Cache.SetExpires(DateTime.Now.AddYears(1));
context.Response.Cache.SetMaxAge(new TimeSpan(365, 0, 0, 0));
context.Response.ContentType = mime;
context.Response.AddHeader("ETag", currentETag);

var disposition = new ContentDisposition
{
    FileName = Path.GetFileName(tempPath),
    Inline = mime.Contains("image")
};
context.Response.AddHeader("content-disposition", disposition.ToString());

try {
   context.Response.TransmitFile(tempPath);
} catch {
   context.Response.TransmitFile(errorUri);
}

额外说明

  • 前端不需要做任何修改,浏览器请求图片时会自动携带If-None-Match请求头,收到304状态码后会自动调用本地缓存的图片资源,不需要JS额外处理。
  • 优化建议:因为你的ETag是基于不变的文件名生成,不需要调用FetchFile读取文件后再生成ETag,可以直接根据fileUri参数拼接出对应的文件名生成ETag,进一步减少IO开销。

内容的提问来源于stack exchange,提问作者StealthRT

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.28 18:54:00