更好的方法来阻止IEcaching在AngularJS?
我目前使用服务/ $资源进行ajax调用(在这种情况下,GET)和IEcaching的调用,使新的数据不能从服务器检索。 我使用了一种技术,我用googlesearch创build一个随机数,并将其附加到请求,以便IE不会去caching数据。
有没有更好的办法比caching添加到每个请求?
工厂代码
.factory('UserDeviceService', function ($resource) { return $resource('/users/:dest', {}, { query: {method: 'GET', params: {dest: "getDevicesByUserID"}, isArray: true } });
来自控制器的呼叫
$scope.getUserDevices = function () { UserDeviceService.query({cacheKill: new Date().getTime()},function (data) { //logic }); }
作为binarygiant要求,我张贴我的评论作为答案。 我已经通过在服务器端的响应中添加No-Cache头来解决这个问题。 请注意,您必须为GET请求执行此操作,其他请求似乎正常工作。
binarygiant发布了如何在node / express上做到这一点。 你可以在ASP.NET MVC中这样做:
[OutputCache(NoStore = true, Duration = 0, VaryByParam = "None")] public ActionResult Get() { // return your response }
正如我的其他post所述 ,你可以在$ httpProvider中全局禁用caching:
myModule.config(['$httpProvider', function($httpProvider) { //initialize get if not there if (!$httpProvider.defaults.headers.get) { $httpProvider.defaults.headers.get = {}; } // Answer edited to include suggestions from comments // because previous version of code introduced browser-related errors //disable IE ajax request caching $httpProvider.defaults.headers.get['If-Modified-Since'] = 'Mon, 26 Jul 1997 05:00:00 GMT'; // extra $httpProvider.defaults.headers.get['Cache-Control'] = 'no-cache'; $httpProvider.defaults.headers.get['Pragma'] = 'no-cache'; }]);
对于那些使用ASP.NET Web API 2的人来说,等效的解决scheme就是这样(Web API不使用与MVC相同的caching逻辑):
public class NoCacheHeaderFilter : ActionFilterAttribute { public override void OnActionExecuted(HttpActionExecutedContext actionExecutedContext) { if (actionExecutedContext.Response != null) // can be null when exception happens { actionExecutedContext.Response.Headers.CacheControl = new CacheControlHeaderValue { NoCache = true, NoStore = true, MustRevalidate = true }; actionExecutedContext.Response.Headers.Pragma.Add(new NameValueHeaderValue("no-cache")); if (actionExecutedContext.Response.Content != null) // can be null (for example HTTP 400) { actionExecutedContext.Response.Content.Headers.Expires = DateTimeOffset.UtcNow; } } } }
然后将其附加在WebApiConfig.cs中:
public static void Register(HttpConfiguration config) { .... config.Filters.Add(new NoCacheHeaderFilter()); config.Routes.MapHttpRoute( name: "DefaultApi", routeTemplate: "api/{controller}/{id}", defaults: new { id = RouteParameter.Optional } ); }
在实例中启用noCache是完成这个任务的最好方法:
在节点/expression这可以防止IEcaching这些请求:
app.use(function noCache(req, res, next) { res.header("Cache-Control", "no-cache, no-store, must-revalidate"); res.header("Pragma", "no-cache"); res.header("Expires", 0); next(); });
你可以添加一个拦截器来生成唯一的请求url。 你也可以删除console.log调用
myModule.config(['$httpProvider', function($httpProvider) { $httpProvider.interceptors.push('noCacheInterceptor'); }]).factory('noCacheInterceptor', function () { return { request: function (config) { console.log(config.method); console.log(config.url); if(config.method=='GET'){ var separator = config.url.indexOf('?') === -1 ? '?' : '&'; config.url = config.url+separator+'noCache=' + new Date().getTime(); } console.log(config.method); console.log(config.url); return config; } }; });
我得到它通过解决:
$http.get("/your_url?rnd="+new Date().getTime()).success(function(data, status, headers, config) { console.log('your get response is new!!!'); });
虽然这种做法:
myModule.config(['$httpProvider', function($httpProvider) { //initialize get if not there if (!$httpProvider.defaults.headers.get) { $httpProvider.defaults.headers.get = {}; } //disable IE ajax request caching $httpProvider.defaults.headers.get['If-Modified-Since'] = '0'; }]);
是正确的,'0'不是If-Modified-Since标题的有效值。 它需要是一个有效的HTTPdate,例如:
If-Modified-Since: Sat, 29 Oct 1994 19:43:31 GMT
根据规范 :
如果接收者必须忽略If-Modified-Since标头字段
收到的字段值不是有效的HTTPdate,或者如果请求
方法既不是GET也不是HEAD。
所以,最好是安全,而不要抱歉,并使用过去的实际date。
如果你有任何控制服务器的输出,最好是不添加caching标题。
Koajs相当于binarygiant的回答:
app.use(route.get('*', noCache)); function* noCache(path, next){ this.set('cache-control', 'no-cache, no-store, must-revalidate'); this.set('pragma', 'no-cache'); this.set('expires', 0); yield next; }
我的解决scheme是在服务器上添加Cache-Control: no-cache
头部,并在改变状态之前添加$templateCache.remove()
。 我正在使用angular-ui / ui-router。 我有问题与IE11和Edge浏览器。
$templateCache.remove('/partials/details.html'); $state.go('details');
一个明显的解决scheme是使用独特的url。 但是,路由器的url如何在初始化后更改禁用浏览器caching不是一个选项,因为我们需要这个正常的操作。 当不再需要这些模板时,可以从$ templateCache中移除模板。 ( http://docs.angularjs.org/api/ng。$ templateCache)。 下载完成后,这些新增加的内容将被添加到caching中。