看起来如果我使用 加载动态内容$.get()
,结果会缓存在浏览器中。
在 QueryString 中添加一些随机字符串似乎可以解决这个问题(我使用new Date().toString()
),但这感觉就像一个 hack。
有没有其他方法可以实现这一目标?或者,如果唯一的字符串是实现这一目标的唯一方法,除了new Date()
?
看起来如果我使用 加载动态内容$.get()
,结果会缓存在浏览器中。
在 QueryString 中添加一些随机字符串似乎可以解决这个问题(我使用new Date().toString()
),但这感觉就像一个 hack。
有没有其他方法可以实现这一目标?或者,如果唯一的字符串是实现这一目标的唯一方法,除了new Date()
?
以下将阻止所有未来的 AJAX 请求被缓存,无论您使用哪种 jQuery 方法($.get、$.ajax 等)
$.ajaxSetup({ cache: false });
JQuery 的 $.get() 将缓存结果。代替
$.get("myurl", myCallback)
您应该使用 $.ajax,这将允许您关闭缓存:
$.ajax({url: "myurl", success: myCallback, cache: false});
这里的所有答案都会在请求的 URL 上留下足迹,该 URL 将显示在服务器的访问日志中。
我需要一个没有副作用的基于标头的解决方案,我发现它可以通过设置如何跨所有浏览器控制网页缓存中提到的标头来实现?.
结果,至少适用于 Chrome,将是:
$.ajax({
url: url,
headers: {
'Cache-Control': 'no-cache, no-store, must-revalidate',
'Pragma': 'no-cache',
'Expires': '0'
}
});
另一种方法是在生成对 ajax 调用的响应的代码中不提供来自服务器端的缓存标头:
response.setHeader( "Pragma", "no-cache" );
response.setHeader( "Cache-Control", "no-cache" );
response.setDateHeader( "Expires", 0 );
就我个人而言,我觉得查询字符串方法比尝试在服务器上设置标头更可靠 - 不能保证代理或浏览器无论如何都不会缓存它(有些浏览器比其他浏览器更糟糕 - 不命名)。
我通常使用Math.random()
,但我认为使用日期没有任何问题(您不应该以足够快的速度执行 AJAX 请求以两次获得相同的值)。
按照文档: http ://api.jquery.com/jquery.ajax/
您可以使用该cache
属性:
$.ajax({
method: "GET",
url: "/Home/AddProduct?",
data: { param1: value1, param2: value2},
cache: false,
success: function (result) {
// TODO
}
});
当然,“缓存破坏”技术将完成工作,但如果服务器向客户端指示不应缓存响应,则首先不会发生这种情况。在某些情况下,缓存响应是有益的,有时则不然。让服务器决定数据的正确生命周期。您可能想稍后更改它。在服务器上比在 UI 代码中的许多不同位置更容易。
当然,如果您无法控制服务器,这将无济于事。
真正的问题是为什么你需要这个不被缓存。如果它不应该被缓存,因为它一直在变化,服务器应该指定不缓存资源。如果它有时只是改变(因为它依赖的资源之一可以改变),并且如果客户端代码有办法知道它,它可以将一个虚拟参数附加到从某个哈希或上次修改日期计算的 url这些资源的一部分(这就是我们在 Microsoft Ajax 脚本资源中所做的,因此它们可以被永久缓存,但新版本仍然可以在它们出现时提供)。如果客户端不知道变化,正确的方法应该是服务器正确处理 HEAD 请求并告诉客户端是否使用缓存版本。在我看来,附加一个随机参数或告诉客户端永远不要缓存是错误的,因为可缓存性是服务器资源的属性,因此应该在服务器端决定。另一个要问自己的问题是,该资源真的应该通过 GET 提供还是应该通过 POST 提供?这是一个语义问题,但它也有安全隐患(只有在服务器允许 GET 时才会发生攻击)。POST 不会被缓存。
也许你应该看一下 $.ajax() (如果你使用的是 jQuery,它看起来像)。看看:http ://docs.jquery.com/Ajax/jQuery.ajax#options和选项“缓存”。
另一种方法是查看您如何在服务器端缓存内容。
使用 POST 请求而不是 GET ...怎么样?(无论如何你应该......)
对于那些在移动 Safari 上使用cache
选项的人$.ajaxSetup()
,看来您可能必须为 POST 使用时间戳,因为移动 Safari 也会缓存它。根据文档$.ajax()
(您被定向到 from $.ajaxSetup()
):
将缓存设置为 false 仅适用于 HEAD 和 GET 请求。它通过将“_={timestamp}”附加到 GET 参数来工作。其他类型的请求不需要该参数,除非在 IE8 中对已由 GET 请求的 URL 进行 POST。
因此,在我上面提到的情况下,单独设置该选项对您没有帮助。
对给出的优秀答案的一个小补充:如果您正在为没有 javascript 的用户使用非 ajax 备份解决方案,那么无论如何您都必须正确获取这些服务器端标头。这不是不可能的,虽然我理解那些放弃它的人;)
我敢肯定还有一个关于 SO 的问题,它将为您提供适当的完整标题集。我并不完全相信老鼠的回复涵盖了所有的基础 100%。
基本上只需添加cache:false;
您认为内容会随着进度而改变的ajax。并且内容不会改变的地方你可以省略这个。这样你每次都会得到新的响应
Internet Explorer 的 Ajax 缓存:您打算怎么做?建议三种方法:
- 向查询字符串添加缓存破坏标记,例如 ?date=[timestamp]。在 jQuery 和 YUI 中,您可以告诉它们自动执行此操作。
- 使用 POST 而不是 GET
- 发送一个 HTTP 响应头,专门禁止浏览器缓存它
正如@Athasach 所说,根据 jQuery 文档,$.ajaxSetup({cache:false})
除了 GET 和 HEAD 请求之外,它不适用于其他请求。
Cache-Control: no-cache
无论如何,您最好还是从您的服务器发回一个标头。它提供了更清晰的关注点分离。
当然,这不适用于您不属于您的项目的服务 url。在这种情况下,您可能会考虑从服务器代码代理第三方服务,而不是从客户端代码调用它。
如果您使用的是 .net ASP MVC,请通过在端点函数上添加以下属性来禁用控制器操作上的缓存:
[OutputCacheAttribute(VaryByParam = "*", Duration = 0, NoStore = true)]
现在,通过在 ajax 请求中启用/禁用缓存选项很容易做到这一点,就像这样
$(function () {
var url = 'your url goes here';
$('#ajaxButton').click(function (e) {
$.ajax({
url: url,
data: {
test: 'value'
},
cache: true, //cache enabled, false to reverse
complete: doSomething
});
});
});
//ToDo after ajax call finishes
function doSomething(data) {
console.log(data);
}
});
如果您使用的是 IE 9,那么您需要在控制器类定义前使用以下内容:
[OutputCache(NoStore = true, Duration = 0, VaryByParam = "*")]
公共类 TestController : 控制器
这将阻止浏览器缓存。
此链接的详细信息:http: //dougwilsonsa.wordpress.com/2011/04/29/disabling-ie9-ajax-response-caching-asp-net-mvc-3-jquery/
其实这解决了我的问题。
添加标题
headers: {
'Cache-Control':'no-cache'
}
附加Math.random()
到请求 url